Skip to content

Commit 0807f82

Browse files
committed
Mock the grid array info.
1 parent 7da764c commit 0807f82

File tree

2 files changed

+28
-15
lines changed

2 files changed

+28
-15
lines changed

src/mdio/core/grid.py

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -140,6 +140,19 @@ def deserialize(self, stream: str) -> Grid:
140140
return Grid(**payload)
141141

142142

143+
class _EmptyGrid:
144+
"""Empty volume for Grid mocking."""
145+
146+
def __init__(self, shape: Sequence[int], dtype: np.dtype = np.bool):
147+
"""Initialize the empty grid."""
148+
self.shape = shape
149+
self.dtype = dtype
150+
151+
def __getitem__(self, item):
152+
"""Get item from the empty grid."""
153+
return self.dtype.type(0)
154+
155+
143156
def _calculate_live_mask_chunksize(grid: Grid) -> Sequence[int]:
144157
"""Calculate the optimal chunksize for the live mask.
145158
@@ -154,8 +167,7 @@ def _calculate_live_mask_chunksize(grid: Grid) -> Sequence[int]:
154167
return _calculate_optimal_chunksize(grid.live_mask, INT32_MAX // 4)
155168
except AttributeError:
156169
# Create an empty array with the same shape and dtype as the live mask would have
157-
empty_array = np.empty(grid.shape[:-1], dtype=np.bool_)
158-
return _calculate_optimal_chunksize(empty_array, INT32_MAX // 4)
170+
return _calculate_optimal_chunksize(_EmptyGrid(grid.shape[:-1]), INT32_MAX // 4)
159171

160172

161173
def _calculate_optimal_chunksize( # noqa: C901

tests/unit/test_auto_chunking.py

Lines changed: 14 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
from mdio.core import Grid
77
from mdio.core.grid import _calculate_live_mask_chunksize
88
from mdio.core.grid import _calculate_optimal_chunksize
9+
from mdio.core.grid import _EmptyGrid
910

1011

1112
def test_small_grid_no_chunking():
@@ -17,7 +18,7 @@ def test_small_grid_no_chunking():
1718
Dimension(coords=range(0, 100, 1), name="sample"),
1819
]
1920
grid = Grid(dims=dims)
20-
grid.live_mask = np.empty((100, 100), dtype=np.bool)
21+
grid.live_mask = _EmptyGrid((100, 100), dtype=np.bool)
2122

2223
result = _calculate_live_mask_chunksize(grid)
2324
assert result == (100, 100)
@@ -46,7 +47,7 @@ def test_large_2d_grid_chunking():
4647
Dimension(coords=range(0, 100, 1), name="sample"),
4748
]
4849
grid = Grid(dims=dims)
49-
grid.live_mask = np.empty((50000, 50000), dtype=np.bool)
50+
grid.live_mask = _EmptyGrid((50000, 50000), dtype=np.bool)
5051

5152
result = _calculate_live_mask_chunksize(grid)
5253

@@ -65,7 +66,7 @@ def test_large_3d_grid_chunking():
6566
Dimension(coords=range(0, 100, 1), name="sample"),
6667
]
6768
grid = Grid(dims=dims)
68-
grid.live_mask = np.empty((1500, 1500, 1500), dtype=np.bool)
69+
grid.live_mask = _EmptyGrid((1500, 1500, 1500), dtype=np.bool)
6970

7071
result = _calculate_live_mask_chunksize(grid)
7172

@@ -96,15 +97,15 @@ def test_prestack_land_survey_chunking():
9697
Dimension(coords=range(0, 1000, 1), name="sample"),
9798
]
9899
grid = Grid(dims=dims)
99-
grid.live_mask = np.empty((1000, 1000, 100, 36), dtype=np.bool)
100+
grid.live_mask = _EmptyGrid((1000, 1000, 100, 36), dtype=np.bool)
100101

101102
result = _calculate_live_mask_chunksize(grid)
102103
assert result == (334, 334, 100, 36)
103104

104105

105106
def test_one_dim_full_chunk():
106107
"""Test one-dimensional volume where the whole dimension can be used as chunk."""
107-
arr = np.empty((100,), dtype=np.int8)
108+
arr = _EmptyGrid((100,), dtype=np.int8)
108109
# With n_bytes = 100, max_elements_allowed = 100, thus optimal chunk should be (100,)
109110
result = _calculate_optimal_chunksize(arr, 100)
110111
assert result == (100,)
@@ -115,7 +116,7 @@ def test_two_dim_optimal():
115116
116117
For a shape of (8,6) with n_bytes=20, the optimal chunk is expected to be (8,2).
117118
"""
118-
arr = np.empty((8, 6), dtype=np.int8)
119+
arr = _EmptyGrid((8, 6), dtype=np.int8)
119120
result = _calculate_optimal_chunksize(arr, 20)
120121
assert result == (4, 4)
121122

@@ -125,7 +126,7 @@ def test_three_dim_optimal():
125126
126127
For a shape of (9,6,4) with n_bytes=100, the expected chunk is (9,2,4).
127128
"""
128-
arr = np.empty((9, 6, 4), dtype=np.int8)
129+
arr = _EmptyGrid((9, 6, 4), dtype=np.int8)
129130
result = _calculate_optimal_chunksize(arr, 100)
130131
assert result == (5, 5, 4)
131132

@@ -135,21 +136,21 @@ def test_minimal_chunk_for_large_dtype():
135136
136137
Using int32 (itemsize=4) with shape (4,5) and n_bytes=4 yields (1,1).
137138
"""
138-
arr = np.empty((4, 5), dtype=np.int32)
139+
arr = _EmptyGrid((4, 5), dtype=np.int32)
139140
result = _calculate_optimal_chunksize(arr, 4)
140141
assert result == (1, 1)
141142

142143

143144
def test_large_nbytes():
144145
"""Test that a very large n_bytes returns the full volume shape as the optimal chunk."""
145-
arr = np.empty((10, 10), dtype=np.int8)
146+
arr = _EmptyGrid((10, 10), dtype=np.int8)
146147
result = _calculate_optimal_chunksize(arr, 1000)
147148
assert result == (10, 10)
148149

149150

150151
def test_two_dim_non_int8():
151152
"""Test with a non-int8 dtype where n_bytes exactly covers the full volume in bytes."""
152-
arr = np.empty((6, 8), dtype=np.int16) # int16 has itemsize 2
153+
arr = _EmptyGrid((6, 8), dtype=np.int16) # int16 has itemsize 2
153154
# Total bytes of full volume = 6*8*2 = 96, so optimal chunk should be (6,8)
154155
result = _calculate_optimal_chunksize(arr, 96)
155156
assert result == (6, 8)
@@ -160,14 +161,14 @@ def test_irregular_dimensions():
160161
161162
For shape (7,5) with n_bytes=35, optimal chunk should be (7,5) since 7*5 = 35.
162163
"""
163-
arr = np.empty((7, 5), dtype=np.int8)
164+
arr = _EmptyGrid((7, 5), dtype=np.int8)
164165
result = _calculate_optimal_chunksize(arr, 35)
165166
assert result == (7, 5)
166167

167168

168169
def test_primes():
169170
"""Test volume with prime dimensions where divisors are limited."""
170-
arr = np.empty((7, 5), dtype=np.int8)
171+
arr = _EmptyGrid((7, 5), dtype=np.int8)
171172
result = _calculate_optimal_chunksize(arr, 23)
172173
assert result == (4, 4)
173174

@@ -206,7 +207,7 @@ def test_grid_gambit():
206207

207208
# Create grid and set live mask
208209
grid = Grid(dims=dims)
209-
grid.live_mask = np.empty(shape, dtype=np.bool)
210+
grid.live_mask = _EmptyGrid(shape, dtype=np.bool)
210211

211212
result = _calculate_live_mask_chunksize(grid)
212213

0 commit comments

Comments
 (0)