Пример #1
0
def test_steps_table(tmp_path):
    path = tmp_path / "test.db"
    database = load_database(path=path)
    make_steps_table(database)
    for status in ["scheduled", "running", "completed"]:
        append_row(
            {
                "status": status,
                "n_iterations": 0,
                "type": "optimization",
                "name": "bla",
            },
            "steps",
            database,
            path,
            False,
        )

    res, _ = read_new_rows(database, "steps", 1, "dict_of_lists")

    expected = {
        "rowid": [2, 3],
        "status": ["running", "completed"],
        "type": ["optimization", "optimization"],
        "name": ["bla", "bla"],
        "n_iterations": [0, 0],
    }
    assert res == expected
Пример #2
0
def test_read_optimization_iteration(tmp_path):
    path = tmp_path / "test.db"
    database = load_database(path=path)

    # add the optimization_iterations table
    make_optimization_iteration_table(database, first_eval={"output": 0.5})
    iteration_data = [
        {"external_params": np.array([0])},
        {"external_params": np.array([1])},
        {"external_params": np.array([2])},
    ]

    for data in iteration_data:
        append_row(data, "optimization_iterations", database, path, False)

    # add the optimization_problem table
    make_optimization_problem_table(database)
    problem_data = {"params": pd.DataFrame(data=[10], columns=["value"])}
    append_row(problem_data, "optimization_problem", database, path, False)

    first_row_calc = read_optimization_iteration(path, 0)
    assert first_row_calc["rowid"] == 1
    calculated_params = first_row_calc["params"]
    expected_params = pd.DataFrame(data=[0], columns=["value"])
    assert_frame_equal(calculated_params, expected_params, check_dtype=False)

    last_row_calc = read_optimization_iteration(path, -1)
    assert last_row_calc["rowid"] == 3
    calculated_params = last_row_calc["params"]
    expected_params = pd.DataFrame(data=[2], columns=["value"])
    assert_frame_equal(calculated_params, expected_params, check_dtype=False)
def test_optimization_status_table(tmp_path):
    path = tmp_path / "test.db"
    database = load_database(path=path)
    make_optimization_status_table(database)
    for status in ["scheduled", "running", "success"]:
        append_row({"status": status}, "optimization_status", database, path, False)

    res, _ = read_new_rows(database, "optimization_status", 1, "dict_of_lists")

    expected = {"rowid": [2, 3], "status": ["running", "success"]}
    assert res == expected
Пример #4
0
def _log_final_status(res, database, path, log_options):
    if isinstance(res["success"],
                  str) and res["success"].startswith("Not reported"):
        status = "unknown"
    elif res["success"]:
        status = "finished successfully"
    else:
        status = "failed"

    fast_logging = log_options.get("fast_logging", False)
    append_row({"status": status}, "optimization_status", database, path,
               fast_logging)
Пример #5
0
def _create_and_initialize_database(logging, log_options, first_eval,
                                    problem_data):
    # extract information
    path = Path(logging)
    fast_logging = log_options.get("fast_logging", False)
    if_table_exists = log_options.get("if_table_exists", "extend")
    if_database_exists = log_options.get("if_database_exists", "extend")

    if "if_exists" in log_options and "if_table_exists" not in log_options:
        warnings.warn(
            "The log_option 'if_exists' was renamed to 'if_table_exists'.")

    if logging.exists():
        if if_database_exists == "raise":
            raise FileExistsError(
                f"The database {logging} already exists and the log_option "
                "'if_database_exists' is set to 'raise'")
        elif if_database_exists == "replace":
            logging.unlink()

    database = load_database(path=path, fast_logging=fast_logging)

    # create the optimization_iterations table
    make_optimization_iteration_table(
        database=database,
        first_eval=first_eval,
        if_exists=if_table_exists,
    )

    # create and initialize the steps table; This is alway extended if it exists.
    make_steps_table(database, if_exists=if_table_exists)

    # create_and_initialize the optimization_problem table
    make_optimization_problem_table(database, if_exists=if_table_exists)

    not_saved = [
        "criterion",
        "criterion_kwargs",
        "constraints",
        "derivative",
        "derivative_kwargs",
        "criterion_and_derivative",
        "criterion_and_derivative_kwargs",
    ]
    problem_data = {
        key: val
        for key, val in problem_data.items() if key not in not_saved
    }

    append_row(problem_data, "optimization_problem", database, path,
               fast_logging)

    return database
Пример #6
0
def test_optimization_iteration_table_scalar(tmp_path, iteration_data):
    path = tmp_path / "test.db"
    database = load_database(path=path)
    make_optimization_iteration_table(database, first_eval={"output": 0.5})
    append_row(iteration_data, "optimization_iterations", database, path, False)
    res = read_last_rows(database, "optimization_iterations", 1, "list_of_dicts")
    assert isinstance(res, list) and isinstance(res[0], dict)
    res = res[0]
    assert res["rowid"] == 1
    assert_array_equal(res["params"], iteration_data["params"])

    for key in ["value", "timestamp"]:
        assert res[key] == iteration_data[key]
Пример #7
0
def test_optimization_problem_table(tmp_path, problem_data):
    path = tmp_path / "test.db"
    database = load_database(path=path)
    make_optimization_problem_table(database)
    append_row(problem_data, "optimization_problem", database, path, False)
    res = read_last_rows(database, "optimization_problem", 1, "list_of_dicts")[0]
    assert res["rowid"] == 1
    for key, expected in problem_data.items():
        if key == "criterion":
            assert res[key](np.ones(3)) == 3
        elif isinstance(expected, np.ndarray):
            assert_array_equal(res[key], expected)
        else:
            assert res[key] == expected
def _log_new_evaluations(
    new_criterion,
    new_derivative,
    x,
    external_x,
    caught_exceptions,
    x_hash,
    database,
    database_path,
    log_options,
):
    """Write the new evaluations and additional information into the database.

    Note: There are some seemingly unnecessary type conversions because sqlalchemy
    can fail silently when called with numpy dtypes instead of the equivalent python
    types.

    """
    data = {
        "external_params": external_x,
        "internal_params": x,
        "timestamp": datetime.datetime.now(),
        "distance_origin": float(np.linalg.norm(x)),
        "distance_ones": float(np.linalg.norm(x - 1)),
        "valid": True,
    }

    if new_derivative is not None:
        data["internal_derivative"] = new_derivative

    if caught_exceptions:
        separator = "\n" + "=" * 80 + "\n"
        data["exceptions"] = separator.join(caught_exceptions)
        data["valid"] = False

    if new_criterion is not None:
        data = {**data, **new_criterion}
        data["value"] = float(data["value"])

    if "suffix" in log_options:
        name = "optimization_iterations" + "_" + log_options["suffix"]
    else:
        name = "optimization_iterations"

    fast_logging = log_options.get("fast_logging", False)

    append_row(data, name, database, database_path, fast_logging)
Пример #9
0
def test_read_table(tmp_path, iteration_data):
    path = tmp_path / "test.db"
    database = load_database(path=path)
    make_optimization_iteration_table(database, first_eval={"output": 0.5})
    for i in range(1, 11):  # sqlalchemy starts counting at 1
        iteration_data["value"] = i
        iteration_data["step"] = i % 2
        append_row(iteration_data, "optimization_iterations", database, path, False)

    table = read_table(
        database=database,
        table_name="optimization_iterations",
        return_type="dict_of_lists",
    )

    assert table["rowid"] == list(range(1, 11))
    assert table["step"] == [1, 0] * 5
Пример #10
0
def test_read_last_rows_stride(tmp_path, iteration_data):
    path = tmp_path / "test.db"
    database = load_database(path=path)
    make_optimization_iteration_table(database, first_eval={"output": 0.5})
    for i in range(1, 11):  # sqlalchemy starts counting at 1
        iteration_data["value"] = i
        append_row(iteration_data, "optimization_iterations", database, path, False)

    res = read_last_rows(
        database=database,
        table_name="optimization_iterations",
        n_rows=3,
        return_type="dict_of_lists",
        stride=2,
    )["value"]

    expected = [6.0, 8.0, 10.0]
    assert res == expected
Пример #11
0
def test_read_last_rows_with_step(tmp_path, iteration_data):
    path = tmp_path / "test.db"
    database = load_database(path=path)
    make_optimization_iteration_table(database, first_eval={"output": 0.5})
    for i in range(1, 11):  # sqlalchemy starts counting at 1
        iteration_data["value"] = i
        iteration_data["step"] = i % 2
        append_row(iteration_data, "optimization_iterations", database, path, False)

    res = read_last_rows(
        database=database,
        table_name="optimization_iterations",
        n_rows=20,
        return_type="dict_of_lists",
        step=0,
    )

    expected = [2, 4, 6, 8, 10]
    assert res["rowid"] == expected
Пример #12
0
def test_update_row(tmp_path, iteration_data):
    path = tmp_path / "test.db"
    database = load_database(path=path)
    make_optimization_iteration_table(database, first_eval={"output": 0.5})
    for i in range(1, 11):  # sqlalchemy starts counting at 1
        iteration_data["value"] = i
        append_row(iteration_data, "optimization_iterations", database, path, False)

    update_row({"value": 20}, 8, "optimization_iterations", database, path, False)

    res = read_new_rows(
        database=database,
        table_name="optimization_iterations",
        last_retrieved=3,
        return_type="dict_of_lists",
    )[0]["value"]

    expected = [4, 5, 6, 7, 20, 9, 10]
    assert res == expected
Пример #13
0
def _create_and_initialize_database(logging, log_options, first_eval,
                                    problem_data):

    # extract information
    path = logging
    fast_logging = log_options.get("fast_logging", False)
    if_exists = log_options.get("if_exists", "extend")
    save_all_arguments = log_options.get("save_all_arguments", False)
    database = load_database(path=path, fast_logging=fast_logging)

    # create the optimization_iterations table
    make_optimization_iteration_table(
        database=database,
        first_eval=first_eval,
        if_exists=if_exists,
    )

    # create and initialize the optimization_status table
    make_optimization_status_table(database, if_exists)
    append_row({"status": "running"}, "optimization_status", database, path,
               fast_logging)

    # create_and_initialize the optimization_problem table
    make_optimization_problem_table(database, if_exists, save_all_arguments)
    if not save_all_arguments:
        not_saved = [
            "criterion",
            "criterion_kwargs",
            "constraints",
            "derivative",
            "derivative_kwargs",
            "criterion_and_derivative",
            "criterion_and_derivative_kwargs",
        ]
        problem_data = {
            key: val
            for key, val in problem_data.items() if key not in not_saved
        }
    append_row(problem_data, "optimization_problem", database, path,
               fast_logging)

    return database
Пример #14
0
def _log_new_evaluations(
    new_criterion,
    new_derivative,
    external_x,
    caught_exceptions,
    db_kwargs,
    fixed_log_data,
):
    """Write the new evaluations and additional information into the database.

    Note: There are some seemingly unnecessary type conversions because sqlalchemy
    can fail silently when called with numpy dtypes instead of the equivalent python
    types.

    """
    data = {
        "params": external_x,
        "timestamp": datetime.datetime.now(),
        "valid": True,
        **fixed_log_data,
    }

    if new_derivative is not None:
        data["internal_derivative"] = new_derivative

    if caught_exceptions:
        separator = "\n" + "=" * 80 + "\n"
        data["exceptions"] = separator.join(caught_exceptions)
        data["valid"] = False

    if new_criterion is not None:
        data = {**data, **new_criterion}
        data["value"] = float(data["value"])

    name = "optimization_iterations"

    append_row(data, name, **db_kwargs)