sain.collections.slice
1# BSD 3-Clause License 2# 3# Copyright (c) 2022-Present, nxtlo 4# All rights reserved. 5# 6# Redistribution and use in source and binary forms, with or without 7# modification, are permitted provided that the following conditions are met: 8# 9# * Redistributions of source code must retain the above copyright notice, this 10# list of conditions and the following disclaimer. 11# 12# * Redistributions in binary form must reproduce the above copyright notice, 13# this list of conditions and the following disclaimer in the documentation 14# and/or other materials provided with the distribution. 15# 16# * Neither the name of the copyright holder nor the names of its 17# contributors may be used to endorse or promote products derived from 18# this software without specific prior written permission. 19# 20# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 21# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 22# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 23# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE 24# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 25# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 26# SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 27# CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 28# OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 29# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 30 31from __future__ import annotations 32 33__all__ = ("Slice", "SliceMut", "SpecContains") 34 35import typing 36from collections import abc as collections 37 38from sain import iter as _iter 39 40T = typing.TypeVar("T") 41 42 43Pattern = T | collections.Iterable[T] 44 45 46class SpecContains(typing.Generic[T]): 47 """Provides a default `contains` method.""" 48 49 __slots__ = () 50 51 @typing.final 52 def contains(self: collections.Container[T], pat: Pattern[T]) -> bool: 53 """Check if `pat` is contained in `self`. 54 55 `pat` here can be either an element of type `T` or an iterable of type `T`. 56 57 If an iterable is passed, it will check if at least one of the elements is in `self`. 58 59 Example 60 ```py 61 vec = Vec([1, 2, 3, 4]) 62 assert vec.contains(1) is True 63 assert vec.contains([3, 4]) is True 64 assert vec.contains(map(int, ['1', '2'])) is True 65 ``` 66 67 The implementation is roughly this simple: 68 ```py 69 if isinstance(pat, Iterable): 70 return any(_ in sequence for _ in pat) 71 return pat in sequence 72 ``` 73 """ 74 if isinstance(pat, collections.Iterable): 75 return any(_ in self for _ in pat) # pyright: ignore - bad type inference. 76 77 return pat in self 78 79 80@typing.final 81class Slice(typing.Generic[T], collections.Sequence[T], SpecContains[T]): 82 """An immutable view over some sequence of type `T`. 83 84 Similar to `&[T]` 85 86 Parameters 87 ---------- 88 ptr : `collections.Sequence[T]` 89 The sequence to point to. 90 """ 91 92 __slots__ = ("__buf",) 93 94 def __init__(self, ptr: collections.Sequence[T]) -> None: 95 self.__buf = ptr 96 97 def into_inner(self) -> collections.Sequence[T]: 98 """Consume this `Slice`, returning the sequence that's being pointed to. 99 100 `self` will no longer reference the sequence. 101 102 Example 103 ------- 104 ```py 105 def from_parts(slice: Slice[int], len: int) -> list[int]: 106 uninit: list[int] = [] 107 uninit.extend(slice.into_inner()[:len]) 108 return uninit 109 110 vec = Vec([1, 2, 3, 4]) 111 new = from_parts(vec.as_ref(), 2) 112 assert new == [1, 2] 113 ``` 114 """ 115 ptr = self.__buf 116 del self.__buf 117 return ptr 118 119 def iter(self) -> _iter.TrustedIter[T]: 120 """Returns an iterator over the slice. 121 122 The iterator yields all items from start to end. 123 124 Example 125 ------- 126 ```py 127 x = Vec([1, 2, 3]) 128 iterator = x.iter() 129 130 assert iterator.next() == Some(1) 131 assert iterator.next() == Some(2) 132 assert iterator.next() == Some(3) 133 assert iterator.next().is_none() 134 ``` 135 """ 136 return _iter.TrustedIter(self.__buf) 137 138 def __len__(self) -> int: 139 return len(self.__buf) 140 141 def __iter__(self) -> collections.Iterator[T]: 142 return iter(self.__buf) 143 144 def __repr__(self) -> str: 145 return repr(self.__buf) 146 147 @typing.overload 148 def __getitem__(self, index: slice) -> Slice[T]: ... 149 150 @typing.overload 151 def __getitem__(self, index: int) -> T: ... 152 153 def __getitem__(self, index: int | slice) -> T | Slice[T]: 154 if isinstance(index, slice): 155 return Slice(self.__buf[index]) 156 157 return self.__buf[index] 158 159 def __eq__(self, other: object, /) -> bool: 160 return self.__buf == other 161 162 def __ne__(self, other: object, /) -> bool: 163 return self.__buf != other 164 165 166@typing.final 167class SliceMut(typing.Generic[T], collections.MutableSequence[T], SpecContains[T]): 168 """A mutable view over some sequence of type `T`. 169 170 Similar to `&mut [T]` 171 172 Parameters 173 ---------- 174 ptr : `collections.MutableSequence[T]` 175 The mutable sequence to point to. 176 """ 177 178 __slots__ = ("__buf",) 179 180 def __init__(self, ptr: collections.MutableSequence[T]) -> None: 181 self.__buf = ptr 182 183 def into_inner(self) -> collections.MutableSequence[T]: 184 """Consume this `SliceMut`, returning the sequence that's being pointed to. 185 186 `self` will no longer reference the sequence. 187 188 Example 189 ------- 190 ```py 191 x = Vec(["x", "y", "z"]) 192 193 # mutable reference to `x` 194 mut_ref = x.as_mut() 195 # make all elements in `x` uppercase, then detach from `mut_ref`. 196 mut_ref.into_inner()[:] = [s.upper() for s in mut_ref] 197 198 assert x == ["X", "Y", "Z"] 199 ``` 200 """ 201 ptr = self.__buf 202 del self.__buf 203 return ptr 204 205 def iter(self) -> _iter.TrustedIter[T]: 206 """Returns an iterator over the slice. 207 208 The iterator yields all items from start to end. 209 210 Example 211 ------- 212 ```py 213 x = Vec([1, 2, 3]) 214 iterator = x.iter() 215 216 assert iterator.next() == Some(1) 217 assert iterator.next() == Some(2) 218 assert iterator.next() == Some(3) 219 assert iterator.next().is_none() 220 ``` 221 """ 222 return _iter.TrustedIter(self.__buf) 223 224 def insert(self, index: int, value: T) -> None: 225 self.__buf.insert(index, value) 226 227 def __len__(self) -> int: 228 return len(self.__buf) 229 230 def __iter__(self) -> collections.Iterator[T]: 231 return iter(self.__buf) 232 233 def __repr__(self) -> str: 234 return repr(self.__buf) 235 236 def __setitem__(self, index: int, item: T) -> None: 237 self.__buf.__setitem__(index, item) 238 239 def __delitem__(self, at: int) -> None: 240 del self.__buf[at] 241 242 @typing.overload 243 def __getitem__(self, index: slice) -> Slice[T]: ... 244 245 @typing.overload 246 def __getitem__(self, index: int) -> T: ... 247 248 def __getitem__(self, index: int | slice) -> T | Slice[T]: 249 if isinstance(index, slice): 250 return Slice(self.__buf[index]) 251 252 return self.__buf[index] 253 254 def __eq__(self, other: object, /) -> bool: 255 return self.__buf == other 256 257 def __ne__(self, other: object, /) -> bool: 258 return self.__buf != other
81@typing.final 82class Slice(typing.Generic[T], collections.Sequence[T], SpecContains[T]): 83 """An immutable view over some sequence of type `T`. 84 85 Similar to `&[T]` 86 87 Parameters 88 ---------- 89 ptr : `collections.Sequence[T]` 90 The sequence to point to. 91 """ 92 93 __slots__ = ("__buf",) 94 95 def __init__(self, ptr: collections.Sequence[T]) -> None: 96 self.__buf = ptr 97 98 def into_inner(self) -> collections.Sequence[T]: 99 """Consume this `Slice`, returning the sequence that's being pointed to. 100 101 `self` will no longer reference the sequence. 102 103 Example 104 ------- 105 ```py 106 def from_parts(slice: Slice[int], len: int) -> list[int]: 107 uninit: list[int] = [] 108 uninit.extend(slice.into_inner()[:len]) 109 return uninit 110 111 vec = Vec([1, 2, 3, 4]) 112 new = from_parts(vec.as_ref(), 2) 113 assert new == [1, 2] 114 ``` 115 """ 116 ptr = self.__buf 117 del self.__buf 118 return ptr 119 120 def iter(self) -> _iter.TrustedIter[T]: 121 """Returns an iterator over the slice. 122 123 The iterator yields all items from start to end. 124 125 Example 126 ------- 127 ```py 128 x = Vec([1, 2, 3]) 129 iterator = x.iter() 130 131 assert iterator.next() == Some(1) 132 assert iterator.next() == Some(2) 133 assert iterator.next() == Some(3) 134 assert iterator.next().is_none() 135 ``` 136 """ 137 return _iter.TrustedIter(self.__buf) 138 139 def __len__(self) -> int: 140 return len(self.__buf) 141 142 def __iter__(self) -> collections.Iterator[T]: 143 return iter(self.__buf) 144 145 def __repr__(self) -> str: 146 return repr(self.__buf) 147 148 @typing.overload 149 def __getitem__(self, index: slice) -> Slice[T]: ... 150 151 @typing.overload 152 def __getitem__(self, index: int) -> T: ... 153 154 def __getitem__(self, index: int | slice) -> T | Slice[T]: 155 if isinstance(index, slice): 156 return Slice(self.__buf[index]) 157 158 return self.__buf[index] 159 160 def __eq__(self, other: object, /) -> bool: 161 return self.__buf == other 162 163 def __ne__(self, other: object, /) -> bool: 164 return self.__buf != other
An immutable view over some sequence of type T.
Similar to &[T]
Parameters
- ptr (
collections.Sequence[T]): The sequence to point to.
98 def into_inner(self) -> collections.Sequence[T]: 99 """Consume this `Slice`, returning the sequence that's being pointed to. 100 101 `self` will no longer reference the sequence. 102 103 Example 104 ------- 105 ```py 106 def from_parts(slice: Slice[int], len: int) -> list[int]: 107 uninit: list[int] = [] 108 uninit.extend(slice.into_inner()[:len]) 109 return uninit 110 111 vec = Vec([1, 2, 3, 4]) 112 new = from_parts(vec.as_ref(), 2) 113 assert new == [1, 2] 114 ``` 115 """ 116 ptr = self.__buf 117 del self.__buf 118 return ptr
Consume this Slice, returning the sequence that's being pointed to.
self will no longer reference the sequence.
Example
def from_parts(slice: Slice[int], len: int) -> list[int]:
uninit: list[int] = []
uninit.extend(slice.into_inner()[:len])
return uninit
vec = Vec([1, 2, 3, 4])
new = from_parts(vec.as_ref(), 2)
assert new == [1, 2]
120 def iter(self) -> _iter.TrustedIter[T]: 121 """Returns an iterator over the slice. 122 123 The iterator yields all items from start to end. 124 125 Example 126 ------- 127 ```py 128 x = Vec([1, 2, 3]) 129 iterator = x.iter() 130 131 assert iterator.next() == Some(1) 132 assert iterator.next() == Some(2) 133 assert iterator.next() == Some(3) 134 assert iterator.next().is_none() 135 ``` 136 """ 137 return _iter.TrustedIter(self.__buf)
Returns an iterator over the slice.
The iterator yields all items from start to end.
Example
x = Vec([1, 2, 3])
iterator = x.iter()
assert iterator.next() == Some(1)
assert iterator.next() == Some(2)
assert iterator.next() == Some(3)
assert iterator.next().is_none()
Inherited Members
167@typing.final 168class SliceMut(typing.Generic[T], collections.MutableSequence[T], SpecContains[T]): 169 """A mutable view over some sequence of type `T`. 170 171 Similar to `&mut [T]` 172 173 Parameters 174 ---------- 175 ptr : `collections.MutableSequence[T]` 176 The mutable sequence to point to. 177 """ 178 179 __slots__ = ("__buf",) 180 181 def __init__(self, ptr: collections.MutableSequence[T]) -> None: 182 self.__buf = ptr 183 184 def into_inner(self) -> collections.MutableSequence[T]: 185 """Consume this `SliceMut`, returning the sequence that's being pointed to. 186 187 `self` will no longer reference the sequence. 188 189 Example 190 ------- 191 ```py 192 x = Vec(["x", "y", "z"]) 193 194 # mutable reference to `x` 195 mut_ref = x.as_mut() 196 # make all elements in `x` uppercase, then detach from `mut_ref`. 197 mut_ref.into_inner()[:] = [s.upper() for s in mut_ref] 198 199 assert x == ["X", "Y", "Z"] 200 ``` 201 """ 202 ptr = self.__buf 203 del self.__buf 204 return ptr 205 206 def iter(self) -> _iter.TrustedIter[T]: 207 """Returns an iterator over the slice. 208 209 The iterator yields all items from start to end. 210 211 Example 212 ------- 213 ```py 214 x = Vec([1, 2, 3]) 215 iterator = x.iter() 216 217 assert iterator.next() == Some(1) 218 assert iterator.next() == Some(2) 219 assert iterator.next() == Some(3) 220 assert iterator.next().is_none() 221 ``` 222 """ 223 return _iter.TrustedIter(self.__buf) 224 225 def insert(self, index: int, value: T) -> None: 226 self.__buf.insert(index, value) 227 228 def __len__(self) -> int: 229 return len(self.__buf) 230 231 def __iter__(self) -> collections.Iterator[T]: 232 return iter(self.__buf) 233 234 def __repr__(self) -> str: 235 return repr(self.__buf) 236 237 def __setitem__(self, index: int, item: T) -> None: 238 self.__buf.__setitem__(index, item) 239 240 def __delitem__(self, at: int) -> None: 241 del self.__buf[at] 242 243 @typing.overload 244 def __getitem__(self, index: slice) -> Slice[T]: ... 245 246 @typing.overload 247 def __getitem__(self, index: int) -> T: ... 248 249 def __getitem__(self, index: int | slice) -> T | Slice[T]: 250 if isinstance(index, slice): 251 return Slice(self.__buf[index]) 252 253 return self.__buf[index] 254 255 def __eq__(self, other: object, /) -> bool: 256 return self.__buf == other 257 258 def __ne__(self, other: object, /) -> bool: 259 return self.__buf != other
A mutable view over some sequence of type T.
Similar to &mut [T]
Parameters
- ptr (
collections.MutableSequence[T]): The mutable sequence to point to.
184 def into_inner(self) -> collections.MutableSequence[T]: 185 """Consume this `SliceMut`, returning the sequence that's being pointed to. 186 187 `self` will no longer reference the sequence. 188 189 Example 190 ------- 191 ```py 192 x = Vec(["x", "y", "z"]) 193 194 # mutable reference to `x` 195 mut_ref = x.as_mut() 196 # make all elements in `x` uppercase, then detach from `mut_ref`. 197 mut_ref.into_inner()[:] = [s.upper() for s in mut_ref] 198 199 assert x == ["X", "Y", "Z"] 200 ``` 201 """ 202 ptr = self.__buf 203 del self.__buf 204 return ptr
Consume this SliceMut, returning the sequence that's being pointed to.
self will no longer reference the sequence.
Example
x = Vec(["x", "y", "z"])
# mutable reference to `x`
mut_ref = x.as_mut()
# make all elements in `x` uppercase, then detach from `mut_ref`.
mut_ref.into_inner()[:] = [s.upper() for s in mut_ref]
assert x == ["X", "Y", "Z"]
206 def iter(self) -> _iter.TrustedIter[T]: 207 """Returns an iterator over the slice. 208 209 The iterator yields all items from start to end. 210 211 Example 212 ------- 213 ```py 214 x = Vec([1, 2, 3]) 215 iterator = x.iter() 216 217 assert iterator.next() == Some(1) 218 assert iterator.next() == Some(2) 219 assert iterator.next() == Some(3) 220 assert iterator.next().is_none() 221 ``` 222 """ 223 return _iter.TrustedIter(self.__buf)
Returns an iterator over the slice.
The iterator yields all items from start to end.
Example
x = Vec([1, 2, 3])
iterator = x.iter()
assert iterator.next() == Some(1)
assert iterator.next() == Some(2)
assert iterator.next() == Some(3)
assert iterator.next().is_none()
S.insert(index, value) -- insert value before index
Inherited Members
47class SpecContains(typing.Generic[T]): 48 """Provides a default `contains` method.""" 49 50 __slots__ = () 51 52 @typing.final 53 def contains(self: collections.Container[T], pat: Pattern[T]) -> bool: 54 """Check if `pat` is contained in `self`. 55 56 `pat` here can be either an element of type `T` or an iterable of type `T`. 57 58 If an iterable is passed, it will check if at least one of the elements is in `self`. 59 60 Example 61 ```py 62 vec = Vec([1, 2, 3, 4]) 63 assert vec.contains(1) is True 64 assert vec.contains([3, 4]) is True 65 assert vec.contains(map(int, ['1', '2'])) is True 66 ``` 67 68 The implementation is roughly this simple: 69 ```py 70 if isinstance(pat, Iterable): 71 return any(_ in sequence for _ in pat) 72 return pat in sequence 73 ``` 74 """ 75 if isinstance(pat, collections.Iterable): 76 return any(_ in self for _ in pat) # pyright: ignore - bad type inference. 77 78 return pat in self
Provides a default contains method.
52 @typing.final 53 def contains(self: collections.Container[T], pat: Pattern[T]) -> bool: 54 """Check if `pat` is contained in `self`. 55 56 `pat` here can be either an element of type `T` or an iterable of type `T`. 57 58 If an iterable is passed, it will check if at least one of the elements is in `self`. 59 60 Example 61 ```py 62 vec = Vec([1, 2, 3, 4]) 63 assert vec.contains(1) is True 64 assert vec.contains([3, 4]) is True 65 assert vec.contains(map(int, ['1', '2'])) is True 66 ``` 67 68 The implementation is roughly this simple: 69 ```py 70 if isinstance(pat, Iterable): 71 return any(_ in sequence for _ in pat) 72 return pat in sequence 73 ``` 74 """ 75 if isinstance(pat, collections.Iterable): 76 return any(_ in self for _ in pat) # pyright: ignore - bad type inference. 77 78 return pat in self
Check if pat is contained in self.
pat here can be either an element of type T or an iterable of type T.
If an iterable is passed, it will check if at least one of the elements is in self.
Example
vec = Vec([1, 2, 3, 4])
assert vec.contains(1) is True
assert vec.contains([3, 4]) is True
assert vec.contains(map(int, ['1', '2'])) is True
The implementation is roughly this simple:
if isinstance(pat, Iterable):
return any(_ in sequence for _ in pat)
return pat in sequence