https://numpy.org/
NumPy. The fundamental package for scientific computing with Python.
https://www.python-course.eu/numpy.php
Numpy Tutorial
Charles R. Harris et al, Array programming with NumPy, Nature 585, 357-362 (2020).
Pauli Virtanen et al, SciPy 1.0: fundamental algorithms for scientific computing in Python, Nature Methods 17, 261-272 (2020).
https://numpy.org/install/
If you already have Python, you can install NumPy with: ANACONDA # Best practice, use an environment rather than install in the base env conda create -n my-env conda activate my-env # If you want to install from conda-forge conda config --env --add channels conda-forge # The actual install command conda install numpy PIP (in a virtual environment) pip install numpy APT (Debian Linux) Packages (with dependencies): python-numpy (Py2.7), python3-numpy (Py3), python-pip, python-pip-whl, python3-pip.
NumPy stands for Numerical Python. NumPy is the fundamental package for scientific computing with Python. It contains among other things [version 1.16.2 in Debian 10]:
NumPy’s main object is the homogeneous multidimensional array. It is a table of elements (usually numbers), all of the same type, indexed by a tuple of non-negative integers. In NumPy dimensions are called 'axes'.
import numpy as np # typical import under the 'np' alias print(np.__version__) # 1.16.2 for Debian 10 # also help(np) at the end a = np.arange(15).reshape(3, 5) # array object # arange() is like range() but returns an array. # np.arange( 10, 30, 5 ) # np.arange( 10, 30, 5, dtype=float ) # np.arange( 0, 2, 0.3 ) # it accepts float arguments print(a) # [[ 0 1 2 3 4] # [ 5 6 7 8 9] # [10 11 12 13 14]] # The shape of an array is the number of elements in each dimension. print(a.shape) # (3, 5), tuple, np.shape(a) print(a.ndim) # 2 print(a.dtype) # dtype('int64'), deduced from the sequence print(a.itemsize) # 8, size of bytes of each element of the array print(a.size) # 15, the number of items print(a.nbytes) # 120 assert a.nbytes == a.size * a.itemsize
lst = [24, 12, 57] arr = np.array([24, 12, 57])
# lst # | # o # +------+-----+-----+-----+ # | info | ref | ref | ref | list object # +------+--|--+--|--+--|--+ 64 + len(lst) * 8 bytes # | | | # o o o # +--+ +--+ +--+ # |24| |12| |57| len(lst) * 28 bytes # +--+ +--+ +--+ # int int int # Total: 64 + len(lst) * 8 + len(lst) * 28
# arr # | # o # +------+----+----+----+ # | info | 24 | 12 | 57 | array object # +------+----+----+----+ 96 + len(arr) * 8 bytes # int int int
# Tests in Python 3 and with a 64-bit laptop. import sys import numpy as np print(sys.getsizeof([])) # 64, empty list print(sys.getsizeof(np.array([]))) # 96, empty array lst = [24, 12, 57] print(sys.getsizeof(lst)) # 88 = 64 + 3 * 8, list object print(sys.getsizeof(lst[0])) # 28, int # This is a minimum estimation, as Python integers can use more than 28 bytes. arr = np.array([24, 12, 57]) print(arr.dtype) # dtype('int64') print(sys.getsizeof(arr)) # 120 = 96 + 3 * 8 arr = np.array([24, 12, 57], dtype="int8") # numbers from -127 to 127 print(sys.getsizeof(arr)) # 99 = 96 + 3 * 1 lst[0] = "alpha" print(sys.getsizeof("")) # 49 print(sys.getsizeof(lst)) # 88, the same print(sys.getsizeof(lst[0])) # 54 = 49 + 5, str print(sys.getsizeof(lst[1])) # 28, int
# Numpy arrays can be like Python lists. arr2 = np.array([1, 2.3, "word"], dtype=object) sys.getsizeof(arr2) # 120 = 96 + 3 * 8 (3 references) sys.getsizeof(arr2[0]) # 28, int sys.getsizeof(arr2[1]) # 24, float sys.getsizeof(arr2[2]) # 53 = 49 + 4, str # Total: 120 + 28 + 24 + 52 = 224 bytes
import timeit import numpy as np N = 1000000 x1 = list(range(N)) y1 = list(range(N)) x2 = np.arange(N) y2 = np.arange(N) print("Testing list comprehension ...") t1 = timeit.Timer(lambda: [x1[i] + y1[i] for i in range(N)]) print(t1.timeit(1)) # single run print("Testing zip ...") t1 = timeit.Timer(lambda: [a+b for (a,b) in zip(x1,y1)]) print(t1.timeit(1)) # single run print("Testing numpy ...") t1 = timeit.Timer(lambda: x2 + y2) print(t1.timeit(1)) # single run # Results: # Testing list comprehension ... # 0.0699481050032773 # Testing zip ... # 0.04706689599697711 # Testing numpy ... # 0.0011762819995055906
# Warning! x1 = list(range(0,120,20)) # [0, 20, 40, 60, 80, 100] y1 = [100] * 6 [a+b for (a,b) in zip(x1,y1)] # [100, 120, 140, 160, 180, 200] x2 = np.arange(0,120,20, dtype="int8") # array([0, 20, 40, 60, 80, 100], dtype=int8) y2 = np.array([100] * 6, dtype="int8") # array([100, 100, 100, 100, 100, 100], dtype=int8) x2 + y2 # array([ 100, 120, -116, -96, -76, -56], dtype=int8) ERROR out of range # Great power comes with great responsibility! (Peter Parker principle)