1

numpy.full() is a great function which allows us to generate an array of specific shape and values. For example,

>>>np.full((2,2),[1,2])
array([[1,2],
       [1,2]])

However, it does not have a built-in option to apply values along a specific axis. So, the following code would not work:

>>>np.full((2,2),[1,2],axis=0)
array([[1,1],
       [2,2]])

Hence, I am wondering how I can create a 10x48x271x397 multidimensional array with values [1,2,3,4,5,6,7,8,9,10] inserted along axis=0? In other words, an array with [1,2,3,4,5,6,7,8,9,10] repeated along the first dimensional axis. Is there a way to do this using numpy.full() or an alternative method?

#Does not work, no axis argument in np.full()
values=[1,2,3,4,5,6,7,8,9,10]
np.full((10, 48, 271, 397), values, axis=0)
1
  • np.full supports broadcasting: np.full((2,2),[[1],[2]]) for your first example. So np.full((10, 48, 271, 397), np.array(values)[:,None,None,None]). Commented Jun 15, 2022 at 18:55

1 Answer 1

2

Edit: adding ideas from Michael Szczesny

import numpy as np

shape = (10, 48, 271, 397)
root = np.arange(shape[0])

You can use np.full or np.broadcast_to (only get a view at creation time):

arr1 = np.broadcast_to(root, shape[::-1]).T
arr2 = np.full(shape[::-1], fill_value=root).T

%timeit np.broadcast_to(root, shape[::-1]).T
%timeit np.full(shape[::-1], fill_value=root).T

# 3.56 µs ± 18.2 ns per loop (mean ± std. dev. of 7 runs, 100,000 loops each)
# 75.6 ms ± 243 µs per loop (mean ± std. dev. of 7 runs, 10 loops each)

And instead of getting the shape backwards and the array backwards again, you can use singleton dimension, but it seems less generalizable:

root = root[:, None, None, None]

arr3 = np.broadcast_to(root, shape)
arr4 = np.full(shape, fill_value=root)

root = np.arange(shape[0])
%timeit root_ = root[:, None, None, None]; np.broadcast_to(root_, shape)
%timeit root_ = root[:, None, None, None]; np.full(shape, fill_value=root_)

# 3.61 µs ± 6.36 ns per loop (mean ± std. dev. of 7 runs, 100,000 loops each)
# 57.5 ms ± 114 µs per loop (mean ± std. dev. of 7 runs, 10 loops each)

Checks that everything is equal and actually what we want:

assert arr1.shape == shape

for i in range(shape[0]):
    sub = arr1[i]
    assert np.all(sub == i)

assert np.all(arr1 == arr2)
assert np.all(arr1 == arr3)
assert np.all(arr1 == arr4)
Sign up to request clarification or add additional context in comments.

1 Comment

This is 6120x faster than np.full on my machine because it's a read-only view of root. But if you only need a view, it is a very nice solution. On the other hand, 5164176 pointers referencing the same element seems to have a rather limited field of application.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.