Skip to content

Commit

Permalink
add supported formats to README (#156)
Browse files Browse the repository at this point in the history
* add supported formats to README

* [pre-commit.ci] auto fixes from pre-commit.com hooks

for more information, see https://pre-commit.ci

* update tests / supported table

* [pre-commit.ci] auto fixes from pre-commit.com hooks

for more information, see https://pre-commit.ci

---------

Co-authored-by: pre-commit-ci[bot] <66853113+pre-commit-ci[bot]@users.noreply.github.com>
  • Loading branch information
PythonFZ and pre-commit-ci[bot] authored Dec 6, 2024
1 parent aaa128b commit 8fc920a
Show file tree
Hide file tree
Showing 4 changed files with 209 additions and 6 deletions.
10 changes: 5 additions & 5 deletions .pre-commit-config.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -33,8 +33,8 @@ repos:
args: [ --fix ]
# Run the formatter.
- id: ruff-format
- repo: https://github.com/executablebooks/mdformat
rev: 0.7.19
hooks:
- id: mdformat
args: ["--wrap=80"]
# - repo: https://github.com/executablebooks/mdformat
# rev: 0.7.19
# hooks:
# - id: mdformat
# args: ["--wrap=80"]
44 changes: 44 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,50 @@ ZnH5MD circumvents two current limitations of the H5MD standard.
first frame. Using this feature will not typically not break ompatibility with
other H5MD tools but can lead to unexpected behaviour.

## Supported

### `atoms.info` entry

`dict` and `list` entries assume python standard types if not otherwise specified.

| Type | ZnH5MD |
|--------------------------|--------|
| `np.ndarray` ||
| `float` ||
| `str` ||
| `dict` ||
| `list` ||
| `list[np.ndarray]` ||
| `dict[str, np.ndarray]` ||
| `list[dict]` ||

### `atoms.arrays`

| Type | ZnH5MD |
|--------------------------|--------|
| `np.ndarray` ||
| `float` ||
| `str` ||
| `dict` ||
| `list` ||
| `list[np.ndarray]` ||
| `dict[str, np.ndarray]` ||
| `list[dict]` ||


### `atoms.calc.results`

| Type | ZnH5MD |
|--------------------------|--------|
| `np.ndarray` ||
| `float` ||
| `str` ||
| `dict` ||
| `list` ||
| `list[np.ndarray]` ||
| `dict[str, np.ndarray]` ||
| `list[dict]` ||

## Current limitations

This is a not necessarily complete list of Limitations that will be fixed
Expand Down
18 changes: 17 additions & 1 deletion tests/conftest.py
Original file line number Diff line number Diff line change
Expand Up @@ -86,10 +86,16 @@ def s22_info_arrays_calc() -> list[ase.Atoms]:
"mlip_stress": np.random.rand(6),
"collection": "s22",
"metadata": {"author": "Jane Doe", "date": "2021-09-01"},
"lst": [1, 2, 3],
# "lst_str": ["Jane Doe", "John Doe"],
# "lst_array": [np.random.rand(3), np.random.rand(3)],
}
)
atoms.new_array("mlip_forces", np.random.rand(len(atoms), 3))
atoms.new_array("mlip_forces_2", np.random.rand(len(atoms), 3))
# atoms.arrays["arr_lst_arr"] = [np.random.rand(3) for _ in range(len(atoms))]
# atoms.arrays["arr_lst"] = [[1, 2, 3] for _ in range(len(atoms))]
# atoms.new_array("arr_str", np.array(["abc" for _ in range(len(atoms))]))
atoms.set_velocities(np.random.rand(len(atoms), 3))
calc = SinglePointCalculator(
atoms, energy=np.random.rand(), forces=np.random.rand(len(atoms), 3)
Expand All @@ -115,7 +121,17 @@ def s22_illegal_calc_results() -> list[ase.Atoms]:
for atoms in ase.collections.s22:
atoms.calc = SinglePointCalculator(atoms)
atoms.calc.results["mlip_energy"] = np.random.rand()

atoms.calc.results["dict"] = {"author": "Jane Doe", "date": "2021-09-01"}
atoms.calc.results["float"] = 3.14
atoms.calc.results["int"] = 42
atoms.calc.results["list"] = [1, 2, 3]
atoms.calc.results["str"] = '{"author": "Jane Doe", "date": "2021-09-01"}'
atoms.calc.results["list_array"] = [np.random.rand(3), np.random.rand(3)]
atoms.calc.results["list_str"] = ["Jane Doe", "John Doe"]
# atoms.calc.results["list_dict"] = [
# {"author": "Jane Doe", "date": "2021-09-01"},
# {"author": "John Doe", "date": "2021-09-02"},
# ]
images.append(atoms)
return images

Expand Down
143 changes: 143 additions & 0 deletions tests/format/test_info_array_calc.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,143 @@
import numpy as np
import numpy.testing as npt
import pytest
from ase.build import molecule
from ase.calculators.singlepoint import SinglePointCalculator

import znh5md


# Define assertion functions for different data types
def assert_equal(actual, expected):
assert actual == expected


def assert_allclose(actual, expected):
npt.assert_allclose(actual, expected)


def assert_allclose_list(actual, expected):
for a, e in zip(actual, expected):
npt.assert_allclose(a, e)


def assert_dict_allclose(actual, expected):
for key in expected:
npt.assert_allclose(actual[key], expected[key])


# Pytest fixtures
@pytest.fixture
def io_fixture(tmp_path):
"""Fixture to initialize the ZnH5MD IO object."""
return znh5md.IO(tmp_path / "test.h5")


@pytest.fixture
def water_molecule():
"""Fixture to provide a simple water molecule."""
return molecule("H2O")


@pytest.mark.parametrize(
"key,value,assert_fn",
[
("str", "Hello World", assert_equal),
("float", 3.14, assert_equal),
("ndarray", np.random.rand(10), assert_allclose),
("list_float", [1.0, 2.0, 3.0], assert_allclose),
("list_str", ["Hello", "World"], assert_equal),
("dict", {"a": 1, "b": 2}, assert_equal),
("dict_str", {"a": "Hello", "b": "World"}, assert_equal),
("list_array", [np.random.rand(10), np.random.rand(10)], assert_allclose_list),
("dict_dict", {"a": {"x": 1, "y": 2}, "b": {"x": 3, "y": 4}}, assert_equal),
# (
# "dict_array",
# {"a": np.random.rand(10), "b": np.random.rand(10)},
# assert_dict_allclose,
# ),
# ("list_dict", [{"a": 1, "b": 2}, {"c": 3, "d": 4}], assert_equal),
],
)
def test_info(io_fixture, water_molecule, key, value, assert_fn):
"""Generic test for different info types."""
# Assign the value to the molecule's info
water_molecule.info[key] = value

# Append to the ZnH5MD IO object
io_fixture.append(water_molecule)

# Retrieve and test
assert_fn(io_fixture[0].info[key], value)
assert key not in io_fixture[0].arrays
assert io_fixture[0].calc is None


@pytest.mark.parametrize(
"key,value,assert_fn",
[
("str", "Hello World", assert_equal),
("float", 3.14, assert_equal),
("ndarray", np.random.rand(10), assert_allclose),
("list_float", [1.0, 2.0, 3.0], assert_allclose),
("list_str", ["Hello", "World"], assert_equal),
("dict", {"a": 1, "b": 2}, assert_equal),
("dict_str", {"a": "Hello", "b": "World"}, assert_equal),
("list_array", [np.random.rand(10), np.random.rand(10)], assert_allclose_list),
("dict_dict", {"a": {"x": 1, "y": 2}, "b": {"x": 3, "y": 4}}, assert_equal),
# (
# "dict_array",
# {"a": np.random.rand(10), "b": np.random.rand(10)},
# assert_dict_allclose,
# ),
# ("list_dict", [{"a": 1, "b": 2}, {"c": 3, "d": 4}], assert_equal),
],
)
def test_calc(io_fixture, water_molecule, key, value, assert_fn):
"""Generic test for different calc types."""
# Assign the value to the molecule's info
water_molecule.calc = SinglePointCalculator(water_molecule)
water_molecule.calc.results[key] = value

# Append to the ZnH5MD IO object
io_fixture.append(water_molecule)

# Retrieve and test
assert_fn(io_fixture[0].calc.results[key], value)
assert key not in io_fixture[0].arrays
assert io_fixture[0].info == {}


@pytest.mark.parametrize(
"key,value,assert_fn",
[
("str", "Hello World", assert_equal),
("float", 3.14, assert_equal),
("ndarray", np.random.rand(10), assert_allclose),
("list_float", [1.0, 2.0, 3.0], assert_allclose),
("list_str", ["Hello", "World"], assert_equal),
("dict", {"a": 1, "b": 2}, assert_equal),
("dict_str", {"a": "Hello", "b": "World"}, assert_equal),
("list_array", [np.random.rand(10), np.random.rand(10)], assert_allclose_list),
("dict_dict", {"a": {"x": 1, "y": 2}, "b": {"x": 3, "y": 4}}, assert_equal),
# (
# "dict_array",
# {"a": np.random.rand(10), "b": np.random.rand(10)},
# assert_dict_allclose,
# ),
# ("list_dict", [{"a": 1, "b": 2}, {"c": 3, "d": 4}], assert_equal),
],
)
def test_arrays(io_fixture, water_molecule, key, value, assert_fn):
"""Generic test for different calc types."""
# Assign the value to the molecule's info
water_molecule.arrays[key] = value

# Append to the ZnH5MD IO object
io_fixture.append(water_molecule)

# Retrieve and test
assert_fn(io_fixture[0].arrays[key], value)
# assert key not in io_fixture[0].arrays
assert io_fixture[0].info == {}
assert io_fixture[0].calc is None

0 comments on commit 8fc920a

Please sign in to comment.