summaryrefslogtreecommitdiff
path: root/numpy/lib/tests/test_stride_tricks.py
diff options
context:
space:
mode:
authorKlaus Zimmermann <klaus.zimmermann@smhi.se>2020-11-05 17:51:16 +0100
committerGitHub <noreply@github.com>2020-11-05 10:51:16 -0600
commit43f80863ba2994a186293d86d516204ef38b0043 (patch)
treee137f2a09cfb71bbc6c142752bd6b0e39617afd0 /numpy/lib/tests/test_stride_tricks.py
parent49d62f84df0a82b10b3623024ca66b1f09958072 (diff)
downloadnumpy-43f80863ba2994a186293d86d516204ef38b0043.tar.gz
ENH: Implement sliding window (gh-17394)
* implement sliding_window_view #7753 Test cases are shown in the issue page. * Add Example Cases * Add step_size and N-dim support * Add shape and step_size check. Remove warning. * Remove shape default Add step_size default's description. * Give proper parameter name 'step' * fix a parameter description mistake * implement test function for sliding_window_view() * implement test function for sliding_window_view() * Fix according to @eric-wieser comments * Change arange to ogrid in Examples * remove np.squeeze on return line * Clarify document to avoid parameter confusion. * add `writable` and more explanation in docs * resolve a write conflit * fixes according to @seberg review * resolve write hazard * remove outdated docs. * change referring according to @mattip. change 'writeable' to 'readonly' as @seberg suggest. remove 'step' as @eric-wieser request * fix test minor error * DOC: Grammar fixes * STY: Add missing line break required by PEP8 * + Change readonly parameter to writeable. + Update writeable description. + Fix a few parameter checks. + Other minor improvements. * Move to new api as proposed by @eric-wieser - Change api to follow suggestion by Eric Wieser in https://github.com/numpy/numpy/pull/10771#issuecomment-524715356 - Update docstring - Add more tests * Improve documentation * Add sliding_window_view to documentation index * Apply suggestions from code review Co-authored-by: Eric Wieser <wieser.eric@gmail.com> * Fix window shape check * Add `sliding_window_view` to __all__ * Add tests for error cases * Add array_function dispatching * Change dispatcher argument defaults to None * Simplify array function dispatching * Added "np." prefix to doctests * Split tests * Improved docstring * Add release note * Fix docstring formatting * Fix doctest * Remove namespacing in documentation indexing * Improve docstring * Improved docstring * Simplified docstring * Improve docstring to make pseudo code stand out * Improve docstring * Add simple application example * Correct release note * Improve link with as_strides * Add note about performance * Tidy up main doc string * Make language on performance warning stronger * Bugfix: pass subok and writeable to as_strided * Add writeable test * Add subok test * Change subok test to use custom array subclass instead of unsupported MaskedArray * Add version added information Co-authored-by: Eric Wieser <wieser.eric@gmail.com> Co-authored-by: Fanjin <fjzeng@ucsd.edu> Co-authored-by: Fanjin Zeng <Fnjn@users.noreply.github.com> Co-authored-by: Eric Wieser <wieser.eric@gmail.com> Co-authored-by: fanjin <fjzeng@outlook.com> Closes gh-7753
Diffstat (limited to 'numpy/lib/tests/test_stride_tricks.py')
-rw-r--r--numpy/lib/tests/test_stride_tricks.py109
1 files changed, 107 insertions, 2 deletions
diff --git a/numpy/lib/tests/test_stride_tricks.py b/numpy/lib/tests/test_stride_tricks.py
index 10d7a19ab..efec5d24d 100644
--- a/numpy/lib/tests/test_stride_tricks.py
+++ b/numpy/lib/tests/test_stride_tricks.py
@@ -6,8 +6,10 @@ from numpy.testing import (
)
from numpy.lib.stride_tricks import (
as_strided, broadcast_arrays, _broadcast_shape, broadcast_to,
- broadcast_shapes,
+ broadcast_shapes, sliding_window_view,
)
+import pytest
+
def assert_shapes_correct(input_shapes, expected_shape):
# Broadcast a list of arrays with the given input shapes and check the
@@ -394,6 +396,109 @@ def test_as_strided():
assert_equal(a.dtype, a_view.dtype)
assert_array_equal([r] * 3, a_view)
+
+class TestSlidingWindowView:
+ def test_1d(self):
+ arr = np.arange(5)
+ arr_view = sliding_window_view(arr, 2)
+ expected = np.array([[0, 1],
+ [1, 2],
+ [2, 3],
+ [3, 4]])
+ assert_array_equal(arr_view, expected)
+
+ def test_2d(self):
+ i, j = np.ogrid[:3, :4]
+ arr = 10*i + j
+ shape = (2, 2)
+ arr_view = sliding_window_view(arr, shape)
+ expected = np.array([[[[0, 1], [10, 11]],
+ [[1, 2], [11, 12]],
+ [[2, 3], [12, 13]]],
+ [[[10, 11], [20, 21]],
+ [[11, 12], [21, 22]],
+ [[12, 13], [22, 23]]]])
+ assert_array_equal(arr_view, expected)
+
+ def test_2d_with_axis(self):
+ i, j = np.ogrid[:3, :4]
+ arr = 10*i + j
+ arr_view = sliding_window_view(arr, 3, 0)
+ expected = np.array([[[0, 10, 20],
+ [1, 11, 21],
+ [2, 12, 22],
+ [3, 13, 23]]])
+ assert_array_equal(arr_view, expected)
+
+ def test_2d_repeated_axis(self):
+ i, j = np.ogrid[:3, :4]
+ arr = 10*i + j
+ arr_view = sliding_window_view(arr, (2, 3), (1, 1))
+ expected = np.array([[[[0, 1, 2],
+ [1, 2, 3]]],
+ [[[10, 11, 12],
+ [11, 12, 13]]],
+ [[[20, 21, 22],
+ [21, 22, 23]]]])
+ assert_array_equal(arr_view, expected)
+
+ def test_2d_without_axis(self):
+ i, j = np.ogrid[:4, :4]
+ arr = 10*i + j
+ shape = (2, 3)
+ arr_view = sliding_window_view(arr, shape)
+ expected = np.array([[[[0, 1, 2], [10, 11, 12]],
+ [[1, 2, 3], [11, 12, 13]]],
+ [[[10, 11, 12], [20, 21, 22]],
+ [[11, 12, 13], [21, 22, 23]]],
+ [[[20, 21, 22], [30, 31, 32]],
+ [[21, 22, 23], [31, 32, 33]]]])
+ assert_array_equal(arr_view, expected)
+
+ def test_errors(self):
+ i, j = np.ogrid[:4, :4]
+ arr = 10*i + j
+ with pytest.raises(ValueError, match='cannot contain negative values'):
+ sliding_window_view(arr, (-1, 3))
+ with pytest.raises(
+ ValueError,
+ match='must provide window_shape for all dimensions of `x`'):
+ sliding_window_view(arr, (1,))
+ with pytest.raises(
+ ValueError,
+ match='Must provide matching length window_shape and axis'):
+ sliding_window_view(arr, (1, 3, 4), axis=(0, 1))
+ with pytest.raises(
+ ValueError,
+ match='window shape cannot be larger than input array'):
+ sliding_window_view(arr, (5, 5))
+
+ def test_writeable(self):
+ arr = np.arange(5)
+ view = sliding_window_view(arr, 2, writeable=False)
+ assert_(not view.flags.writeable)
+ with pytest.raises(
+ ValueError,
+ match='assignment destination is read-only'):
+ view[0, 0] = 3
+ view = sliding_window_view(arr, 2, writeable=True)
+ assert_(view.flags.writeable)
+ view[0, 1] = 3
+ assert_array_equal(arr, np.array([0, 3, 2, 3, 4]))
+
+ def test_subok(self):
+ class MyArray(np.ndarray):
+ pass
+
+ arr = np.arange(5).view(MyArray)
+ assert_(not isinstance(sliding_window_view(arr, 2,
+ subok=False),
+ MyArray))
+ assert_(isinstance(sliding_window_view(arr, 2, subok=True), MyArray))
+ # Default behavior
+ assert_(not isinstance(sliding_window_view(arr, 2), MyArray))
+
+
def as_strided_writeable():
arr = np.ones(10)
view = as_strided(arr, writeable=False)
@@ -496,7 +601,7 @@ def test_writeable():
# check: no warning emitted
assert_equal(result.flags.writeable, True)
result[:] = 0
-
+
# keep readonly input readonly
original.flags.writeable = False
_, result = broadcast_arrays(0, original)