60 lines
1.7 KiB
Python
60 lines
1.7 KiB
Python
from pathlib import Path
|
|
|
|
from composer_ans.hopfield import HopfieldParams, generate_next_note, run_hopfield_network
|
|
from composer_ans.io.legacy_files import extract_active_hopfield_submatrix, load_hopfield_weight_matrix
|
|
|
|
|
|
THES = Path(__file__).resolve().parents[1] / "THES"
|
|
|
|
|
|
def deterministic_noise(mean: float, variance: float) -> float:
|
|
return mean
|
|
|
|
|
|
def test_hopfield_zero_matrix_converges_to_first_note_for_blank_column() -> None:
|
|
zero_matrix = tuple(tuple(0.0 for _ in range(40)) for _ in range(40))
|
|
|
|
result = generate_next_note(
|
|
[1, 2, 3, 4, 0],
|
|
zero_matrix,
|
|
noise=deterministic_noise,
|
|
)
|
|
|
|
assert result.output_notes[:4] == (1, 2, 3, 4)
|
|
assert result.candidate_note == 1
|
|
assert result.iterations > 0
|
|
|
|
|
|
def test_generic_hopfield_core_runs_on_arbitrary_grid_shape() -> None:
|
|
inputs = (
|
|
(0.8, 0.2),
|
|
(0.1, 0.9),
|
|
(0.4, 0.3),
|
|
)
|
|
size = len(inputs) * len(inputs[0])
|
|
weights = tuple(tuple(0.0 for _ in range(size)) for _ in range(size))
|
|
|
|
result = run_hopfield_network(inputs, weights)
|
|
|
|
assert result.iterations > 0
|
|
assert len(result.state.outputs) == 3
|
|
assert len(result.state.outputs[0]) == 2
|
|
|
|
|
|
def test_hopfield_legacy_matrix_runs_with_deterministic_noise() -> None:
|
|
matrix = extract_active_hopfield_submatrix(load_hopfield_weight_matrix(THES / "HTN.DAT"))
|
|
|
|
result = generate_next_note(
|
|
[1, 4, 5, 1, 0],
|
|
matrix,
|
|
params=HopfieldParams(),
|
|
noise=deterministic_noise,
|
|
)
|
|
|
|
assert len(result.output_notes) == 5
|
|
assert all(1 <= note <= 8 for note in result.output_notes)
|
|
assert 1 <= result.candidate_note <= 8
|
|
assert result.iterations > 0
|
|
assert len(result.outputs) == 8
|
|
assert len(result.outputs[0]) == 5
|