@@ -2498,6 +2498,33 @@ def clear_memos(self):
24982498 del self.memoized
24992499 self.memoized = {}
25002500
2501+ @staticmethod
2502+ def is_numeric_array(o):
2503+ is_np = isinstance(o, np.ndarray) and o.dtype.kind in 'iuf'
2504+ is_py = isinstance(o, (tuple, list)) and all([isinstance(x, (int, float, bool)) for x in o])
2505+ return is_np or is_py
2506+
2507+ @staticmethod
2508+ def is_bool_array(o):
2509+ if isinstance(o, np.ndarray):
2510+ try:
2511+ return np.issubdtype(o.dtype, np.bool)
2512+ except AttributeError:
2513+ return issubclass(o.dtype.type, np.bool_)
2514+ else:
2515+ return all([isinstance(x, bool) for x in o])
2516+
2517+ @classmethod
2518+ def _json_default(cls, o):
2519+ if isinstance(o, np.ndarray):
2520+ if cls.is_bool_array(o):
2521+ return o.astype(np.int_).tolist()
2522+ return o.tolist()
2523+ if issubclass(o, np.generic):
2524+ return o.__name__
2525+ msg = f'Object of type {o.__class__.__name__} is not JSON serializable'
2526+ raise TypeError(msg)
2527+
25012528 def _to_json_dict(self, array_representation="json-native",
25022529 skipkeys: list[str] | tuple[str] | set[str] | None = None,
25032530 net_name=None, extra=None):
@@ -2530,30 +2557,6 @@ def _to_json_dict(self, array_representation="json-native",
25302557 varnames = set(self.eqvars) - skipkeys
25312558 arep = array_representation
25322559
2533- def is_numeric_array(o):
2534- is_np = isinstance(o, np.ndarray) and o.dtype.kind in 'iuf'
2535- is_py = isinstance(o, (tuple, list)) and all([isinstance(x, (int, float, bool)) for x in o])
2536- return is_np or is_py
2537-
2538- def is_bool_array(o):
2539- if isinstance(o, np.ndarray):
2540- try:
2541- return np.issubdtype(o.dtype, np.bool)
2542- except AttributeError:
2543- return issubclass(o.dtype.type, np.bool_)
2544- else:
2545- return all([isinstance(x, bool) for x in o])
2546-
2547- def default(self, o):
2548- if isinstance(o, np.ndarray):
2549- if is_bool_array(o):
2550- return o.astype(np.int_).tolist()
2551- return o.tolist()
2552- if issubclass(o, np.generic):
2553- return o.__name__
2554- msg = f'Object of type {o.__class__.__name__} is not JSON serializable'
2555- raise TypeError(msg)
2556-
25572560 def get_dtype(o):
25582561 byteorder = o.dtype.byteorder
25592562 if byteorder == '=':
@@ -2572,15 +2575,15 @@ def get_dtype(o):
25722575 data = {var: getattr(self, var) for var in varnames}
25732576
25742577 for k, v in data.items():
2575- if is_numeric_array(v) and is_bool_array(v):
2578+ if self. is_numeric_array(v) and self. is_bool_array(v):
25762579 data[k] = np.asarray(v, dtype=np.int_).tolist()
25772580 elif arep in ["base85", "base64"]:
25782581 from base64 import b85encode, b64encode
25792582 encode = b85encode if arep == "base85" else b64encode
25802583 data = {var: getattr(self, var) for var in varnames}
25812584 for k, v in data.items():
2582- if is_numeric_array(v):
2583- dtype = self.dbin if is_bool_array(v) else self.dd
2585+ if self. is_numeric_array(v):
2586+ dtype = self.dbin if self. is_bool_array(v) else self.dd
25842587 arr = np.asarray(v, dtype=dtype)
25852588 data[k] = {
25862589 "dtype": get_dtype(arr),
@@ -2590,8 +2593,6 @@ def get_dtype(o):
25902593 else:
25912594 raise ValueError("array_representation must be 'json-native' or 'base85'.")
25922595
2593- json.JSONEncoder.default = default
2594-
25952596 d = {
25962597 "$schema": "https://ornl.github.io/superneuromat/schema/0.1/snn.json",
25972598 "version": "0.1",
@@ -2654,8 +2655,9 @@ def to_json(self, array_representation="json-native",
26542655 >>> snn.to_json(net_name="My SNN", indent=None)
26552656 {"$schema": "https://ornl.github.io/superneuromat/schema/0.1/snn.json", "version": "0.1", "networks": [{"meta": {"array_representation": "json-native", "from": {"module": "superneuromat", "version": "3.1.0"}, "format": "snm", "format_version": "0.1", "type": "SNN"}, "data": {"neuron_refractory_periods": [0, 0], "neuron_states": [0.0, 0.0], "num_synapses": 2, "post_synaptic_neuron_ids": [1, 0], "aneg": [], "enable_stdp": [0, 0], "pre_synaptic_neuron_ids": [0, 1], "neuron_thresholds": [3.141592653589793115997963468544185161590576171875, 0.0], "neuron_refractory_periods_state": [0.0, 0.0], "neuron_reset_states": [0.0, 0.0], "stdp_positive_update": true, "input_spikes": {"3": {"nids": [1], "values": [1.0]}}, "synaptic_delays": [1, 1], "allow_signed_leak": false, "num_neurons": 2, "_sparse": "auto", "_backend": "auto", "apos": [], "manual_setup": false, "spike_train": [[1, 0], [0, 1], [0, 0], [0, 0], [0, 0], [0, 0], [0, 0], [0, 0], [0, 0], [0, 0]], "neuron_leaks": [Infinity, Infinity], "allow_incorrect_stdp_sign": false, "stdp": true, "synaptic_weights": [1.0, 1.0], "default_dtype": "float64", "stdp_negative_update": true}}]}
26562657 """ # noqa: E501 (line length)
2658+
26572659 d = self._to_json_dict(array_representation, skipkeys=skipkeys, net_name=net_name, extra=extra)
2658- return json.dumps(d, indent=indent, **kwargs)
2660+ return json.dumps(d, indent=indent, default=self._json_default, **kwargs)
26592661
26602662 def saveas_json(self, fp,
26612663 array_representation="json-native",
@@ -2691,7 +2693,7 @@ def saveas_json(self, fp,
26912693 >>> snn.saveas_json(f, net_name="My SNN")
26922694 """
26932695 d = self._to_json_dict(array_representation, skipkeys=skipkeys, net_name=net_name, extra=extra)
2694- return json.dump(d, fp, indent=indent, **kwargs)
2696+ return json.dump(d, fp, indent=indent, default=self._json_default, **kwargs)
26952697
26962698 def from_json_network(self, net_dict: dict, skipkeys: list[str] | tuple[str] | set[str] | None = None):
26972699 from base64 import b85decode, b64decode
0 commit comments