v923z / micropython-ulab

a numpy-like fast vector module for micropython, circuitpython, and their derivatives

Home Page:https://micropython-ulab.readthedocs.io/en/latest

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

shape order

iabdalkader opened this issue · comments

Hi!! Not really a bug but I was wondering if storing the array's shape in reverse is by design ?

For example, with 1x36 array, NDMIS=4 the shape looks like this:

$23 = {base = {type = 0x80195330 <ulab_ndarray_type>}, dtype = 98 'b', itemsize = 1 '\001', boolean = 0 '\000', 
  ndim = 2 '\002', len = 36, shape = {0, 0, 1, 36}, strides = {0, 0, 36, 1}, array = 0x80098a0, origin = 0x80098a0}

Naturally I expected the shape to be {1, 36, 0, 0}. Is there an option to reverse it back ?

import ulab
print(ulab.__version__)

6.5.2-(3)D

To Reproduce
Build with NDIMS > 1 Create an array and print shape.

This is the convention adopted by numpy:

>>> import numpy as np
>>> np.ones((1, 36), dtype=np.uint8).strides
(36, 1)
>>> np.ones((1, 36), dtype=np.uint8).shape
(1, 36)

and ulab follows that:

>>> from ulab import numpy as np
>>> np.ones((1, 36), dtype=np.uint8).strides
(36, 1)
>>> np.ones((1, 36), dtype=np.uint8).shape
(1, 36)

The reason is that it's much easier to deal with the nested loops, if the last dimension of the array (the one that has the smallest stride) is in the innermost loop. This is especially true in the case of ulab, where, for the sake of performance, storage etc., the dimension is fixed at compile time.

Ah I see. Thanks for the clarification! I've updated my code to something like this:

for (size_t i = 0; i < input_array->ndim; i++) {
    size_t ulab_offset = ULAB_MAX_DIMS - input_array->ndim;
    if (input_array->shape[ulab_offset + i] != mp_obj_get_int(input_shape->items[i])) {