Decompose outer indexer to the successive two indexers, where the first indexer will be used to index backend arrays, while the second one is used to index the loaded on-memory np.ndarray. Parameters ---------- indexer : OuterIndexer or BasicIndexer indexing_support : O
(
indexer: BasicIndexer | OuterIndexer,
shape: _Shape,
indexing_support: IndexingSupport,
)
| 1317 | |
| 1318 | |
| 1319 | def _decompose_outer_indexer( |
| 1320 | indexer: BasicIndexer | OuterIndexer, |
| 1321 | shape: _Shape, |
| 1322 | indexing_support: IndexingSupport, |
| 1323 | ) -> tuple[ExplicitIndexer, ExplicitIndexer]: |
| 1324 | """ |
| 1325 | Decompose outer indexer to the successive two indexers, where the |
| 1326 | first indexer will be used to index backend arrays, while the second one |
| 1327 | is used to index the loaded on-memory np.ndarray. |
| 1328 | |
| 1329 | Parameters |
| 1330 | ---------- |
| 1331 | indexer : OuterIndexer or BasicIndexer |
| 1332 | indexing_support : One of the entries of IndexingSupport |
| 1333 | |
| 1334 | Returns |
| 1335 | ------- |
| 1336 | backend_indexer: OuterIndexer or BasicIndexer |
| 1337 | np_indexers: an ExplicitIndexer (OuterIndexer / BasicIndexer) |
| 1338 | |
| 1339 | Notes |
| 1340 | ----- |
| 1341 | This function is used to realize the vectorized indexing for the backend |
| 1342 | arrays that only support basic or outer indexing. |
| 1343 | |
| 1344 | As an example, let us consider to index a few elements from a backend array |
| 1345 | with an orthogonal indexer ([0, 3, 1], [2, 3, 2]). |
| 1346 | Even if the backend array only supports basic indexing, it is more |
| 1347 | efficient to load a subslice of the array than loading the entire array, |
| 1348 | |
| 1349 | >>> array = np.arange(36).reshape(6, 6) |
| 1350 | >>> backend_indexer = BasicIndexer((slice(0, 3), slice(2, 4))) |
| 1351 | >>> # load subslice of the array |
| 1352 | ... array = NumpyIndexingAdapter(array)[backend_indexer] |
| 1353 | >>> np_indexer = OuterIndexer((np.array([0, 2, 1]), np.array([0, 1, 0]))) |
| 1354 | >>> # outer indexing for on-memory np.ndarray. |
| 1355 | ... NumpyIndexingAdapter(array).oindex[np_indexer] |
| 1356 | array([[ 2, 3, 2], |
| 1357 | [14, 15, 14], |
| 1358 | [ 8, 9, 8]]) |
| 1359 | """ |
| 1360 | backend_indexer: list[Any] = [] |
| 1361 | np_indexer: list[Any] = [] |
| 1362 | |
| 1363 | assert isinstance(indexer, OuterIndexer | BasicIndexer) |
| 1364 | |
| 1365 | if indexing_support == IndexingSupport.VECTORIZED: |
| 1366 | for k, s in zip(indexer.tuple, shape, strict=False): |
| 1367 | if isinstance(k, slice): |
| 1368 | # If it is a slice, then we will slice it as-is |
| 1369 | # (but make its step positive) in the backend, |
| 1370 | bk_slice, np_slice = _decompose_slice(k, s) |
| 1371 | backend_indexer.append(bk_slice) |
| 1372 | np_indexer.append(np_slice) |
| 1373 | else: |
| 1374 | backend_indexer.append(k) |
| 1375 | if not is_scalar(k): |
| 1376 | np_indexer.append(slice(None)) |
no test coverage detected
searching dependent graphs…