1c822d5Add modal-series and fd-second-order submissions for string-pluck-v1, with results workflowJeremy Magland 1"""Shared helpers for the example solvers: load the challenge, write wavs, write submission JSON."""
2from __future__ import annotations
4import json
5import platform
6from pathlib import Path
8import numpy as np
9from scipy.io import wavfile
12def load_challenge(path: Path) -> dict:
13 with open(path) as f:
14 return json.load(f)
17def write_wav(path: Path, samples_si: np.ndarray, challenge: dict) -> None:
18 """Write pointwise samples of the SI signal, divided by signal_scale, as float32."""
19 out = challenge["output"]
20 scaled = np.asarray(samples_si, dtype=np.float64) / float(out["signal_scale"])
21 path.parent.mkdir(parents=True, exist_ok=True)
22 wavfile.write(path, int(out["sample_rate_hz"]), scaled.astype(np.float32))
25def hardware_string() -> str:
26 cpu = platform.processor() or platform.machine()
27 try:
28 with open("/proc/cpuinfo") as f:
29 for line in f:
30 if line.startswith("model name"):
31 cpu = line.split(":", 1)[1].strip()
32 break
33 except OSError:
34 pass
35 return f"{cpu}, single thread, Python {platform.python_version()} + numpy {np.__version__}"
38def initial_shape(x: np.ndarray, p: dict) -> np.ndarray:
39 """Raised-cosine pluck u_0(x) from the challenge spec."""
40 d = x - p["x_p"]
41 u = np.zeros_like(x)
42 m = np.abs(d) <= p["w"]
43 u[m] = 0.5 * p["h"] * (1.0 + np.cos(np.pi * d[m] / p["w"]))
44 return u