Source code for smash.io.mesh_io
from __future__ import annotations
from smash.io._error import ReadHDF5MethodError
import os
import errno
import h5py
import numpy as np
__all__ = ["save_mesh", "read_mesh"]
def _parse_mesh_dict_to_hdf5(mesh: dict, hdf5_ins):
for key, value in mesh.items():
if isinstance(value, np.ndarray):
if value.dtype.char == "U":
value = value.astype("S")
hdf5_ins.create_dataset(
key,
shape=value.shape,
dtype=value.dtype,
data=value,
compression="gzip",
chunks=True,
)
else:
hdf5_ins.attrs[key] = value
def _parse_hdf5_to_mesh_dict(hdf5_ins) -> dict:
mesh = {}
attr_keys = list(hdf5_ins.attrs.keys())
attr_keys.remove("_save_func")
keys = list(hdf5_ins.keys())
ac_check = "active_cell" in keys
for key in attr_keys:
mesh[key] = hdf5_ins.attrs[key]
for key in keys:
if key in ["flwdir", "flwdst", "flwacc"] and ac_check:
mesh[key] = np.ma.masked_array(
hdf5_ins[key][:], mask=(1 - hdf5_ins["active_cell"][:])
)
elif key == "code":
mesh[key] = hdf5_ins[key][:].astype("U")
else:
mesh[key] = hdf5_ins[key][:]
return mesh
[docs]def save_mesh(mesh: dict, path: str):
"""
Save Model initialization mesh dictionary.
Parameters
----------
mesh : dict
The mesh dictionary to be saved to `HDF5 <https://www.hdfgroup.org/solutions/hdf5/>`__ file.
path : str
The file path. If the path not end with ``.hdf5``, the extension is automatically added to the file path.
See Also
--------
read_mesh: Read Model initialization mesh dictionary.
Examples
--------
>>> setup, mesh = smash.load_dataset("cance")
>>> mesh
{'dx': 1000.0, 'nac': 383, 'ncol': 28, 'ng': 3, 'nrow': 28 ...}
Save mesh
>>> smash.save_mesh(mesh, "mesh.hdf5")
Read mesh
>>> mesh_rld = smash.read_mesh("mesh.hdf5")
{'dx': 1000.0, 'nac': 383, 'ncol': 28, 'ng': 3, 'nrow': 28, ...}
"""
if not path.endswith(".hdf5"):
path = path + ".hdf5"
with h5py.File(path, "w") as f:
_parse_mesh_dict_to_hdf5(mesh, f)
f.attrs["_save_func"] = "save_mesh"
[docs]def read_mesh(path: str) -> dict:
"""
Read Model initialization mesh dictionary.
Parameters
----------
path : str
The file path.
Returns
-------
dict :
A mesh dictionary loaded from HDF5 file.
Raises
------
FileNotFoundError:
If file not found.
ReadHDF5MethodError:
If file not created with `save_mesh`.
See Also
--------
save_mesh: Save Model initialization mesh dictionary.
Examples
--------
>>> setup, mesh = smash.load_dataset("cance")
>>> mesh
{'dx': 1000.0, 'nac': 383, 'ncol': 28, 'ng': 3, 'nrow': 28 ...}
Save mesh
>>> smash.save_mesh(mesh, "mesh.hdf5")
Read mesh
>>> mesh_rld = smash.read_mesh("mesh.hdf5")
{'dx': 1000.0, 'nac': 383, 'ncol': 28, 'ng': 3, 'nrow': 28, ...}
"""
if os.path.isfile(path):
with h5py.File(path, "r") as f:
if f.attrs.get("_save_func") == "save_mesh":
return _parse_hdf5_to_mesh_dict(f)
else:
raise ReadHDF5MethodError(
f"Unable to read '{path}' with 'read_mesh' method. The file may not have been created with 'save_mesh' method."
)
else:
raise FileNotFoundError(errno.ENOENT, os.strerror(errno.ENOENT), path)