-
[python]5. Numpy인공지능/부스트캠프 Ai Tech 2022. 1. 21. 18:40728x90
[python]5. Numpy In [1]:from IPython.core.display import display, HTML display(HTML("<style>.container { width:90% !important; }</style>")) #창 맞추기위함
5. Numpy¶
Numpy(Numerical Python)¶
고성능 과학 계산용 패키지
- 일반 List에 비해 빠르고, 메모리 효율적
- 반복문 없이 데이터 배열에 대한 처리를 지원
- C, C++, 포트란 등의 언어와 통합 가능
In [17]:import numpy as np
array creation¶
- numpy는 np.array 함수를 활용할 배열을 생성
- 하나의 데이터 type만 배열에 넣을 수 있음
ex) List = [1, 0.7, 0.5] 와 같이 int와 float이 함께 들어가지 못함
In [4]:a = [1,2,3,4,5] a = np.array(a, int)
In [5]:a
Out[5]:array([1, 2, 3, 4, 5])
In [7]:test_array = np.array(["1", "4", 5.0, 8], float) print(test_array)
[1. 4. 5. 8.]
In [6]:type(test_array)
Out[6]:numpy.ndarray
In [8]:type(test_array[3])
Out[8]:numpy.float64
np.array는 자체로 값을 가지고 있지만, 파이썬의 list는 linked-list 의 형태로 값의 주소를 저장하여 호출시 불러오는 형태이다.
In [12]:a = [1,2,3,4,5] b = [5,4,3,2,1] a[0] is b[-1] # 1을 갖고있는 주소가 같다.
Out[12]:True
In [13]:a[1] is b[-2]
Out[13]:True
In [11]:a = np.array(a) b = np.array(b) a[1] is b[-2]
Out[11]:False
- shape : np.array의 dimension 구성을 반환함
- dtype : np.array의 데이터 type을 반환함
In [14]:test_array.dtype # Array(배열) 전체의 데이터 Type을 반환함
Out[14]:dtype('float64')
In [15]:a = [[1,2,3], [4,5,6], [4,5,6]]
In [16]:np.array(a).shape
Out[16]:(3, 3)
array shape¶
array의 RANK에 따라 불리는 이름이 있음
Rank 0 : scalar, 1 : vector, 2 : matrix, 3 : 3-tensor, n : n-tensor
array shape(vector)¶
In [17]:test_array = np.array([1, 4, 5, "8"], float) test_array
Out[17]:array([1., 4., 5., 8.])
In [18]:test_array.shape # RANK 1, type =tuple
Out[18]:(4,)
array shape(matrix)¶
In [19]:matrix = [[1,2,5,8],[1,2,5,8],[1,2,5,8]] np.array(matrix, int).shape #RANK 2, type =tuple
Out[19]:(3, 4)
array shape(3d order tensor)¶
In [24]:tensor = [[[1,2,5,8],[1,2,5,8],[1,2,5,8]], [[1,2,5,8],[1,2,5,8],[1,2,5,8]], [[1,2,5,8],[1,2,5,8],[1,2,5,8]], [[1,2,5,8],[1,2,5,8],[1,2,5,8]]]
In [25]:np.array(tensor,int).shape # RANK 3, type =tuple
Out[25]:(4, 3, 4)
- ndim : number of dimensions , 차원의 갯수, RANK
- size - data의 개수
array dtype¶
- ndarray의 single element가 가지는 data type
- 각 element가 차지하는 memory의 크기로 결정됨
In [26]:np.array([[1,2,3], [4.5, 5, 6]], dtype=int)
Out[26]:array([[1, 2, 3], [4, 5, 6]])
In [28]:np.array([[1,2,3], [4.5, "5", "6"]], dtype=np.float32) # 32bits = 4bytes, 6 * 4bytes
Out[28]:array([[1. , 2. , 3. ], [4.5, 5. , 6. ]], dtype=float32)
In [29]:np.array([[1,2,3], [4.5, "5", "6"]], dtype=np.float64) # 64bits = 8bytes, 6 * 8bytes
Out[29]:array([[1. , 2. , 3. ], [4.5, 5. , 6. ]])
In [30]:np.array([[1,2,3], [4.5, "5", "6"]], dtype=np.int8) # 8bits = 1bytes , 6 * 1 bytes
Out[30]:array([[1, 2, 3], [4, 5, 6]], dtype=int8)
Handling shape¶
- reshape : Array의 shape의 크기를 변경
In [31]:test_matrix = [[1,2,3,4], [1,2,5,8]] np.array(test_matrix).shape
Out[31]:(2, 4)
In [32]:np.array(test_matrix).reshape(8,)
Out[32]:array([1, 2, 3, 4, 1, 2, 5, 8])
In [33]:np.array(test_matrix).reshape(8,).shape
Out[33]:(8,)
In [35]:np.array(test_matrix).reshape(-1,2).shape # -1 : size를 기반으로 row 개수 선정
Out[35]:(4, 2)
In [36]:np.array(test_matrix).reshape(-1,2,2)
Out[36]:array([[[1, 2], [3, 4]], [[1, 2], [5, 8]]])
flatten¶
다차원 array를 1차원 array로 변환
In [37]:test_matrix = [[[1,2,3,4], [1,2,5,8]], [[1,2,3,4], [1,2,5,8]]] np.array(test_matrix).shape
Out[37]:(2, 2, 4)
In [38]:np.array(test_matrix).flatten()
Out[38]:array([1, 2, 3, 4, 1, 2, 5, 8, 1, 2, 3, 4, 1, 2, 5, 8])
In [39]:np.array(test_matrix).flatten().shape
Out[39]:(16,)
indexing & slicing¶
list와 달리 이차원 배열에서 [0,0] 표기법을 제공
In [40]:a = np.array([[1,2,3], [4.5, 5, 6]], int)
In [41]:print(a)
[[1 2 3] [4 5 6]]
In [42]:print(a[0,0]) # array에서 가능한 표현
1
In [43]:print(a[0][0])
1
In [44]:a[0, 0] = 10 # Matrix 0,0 에 10 할당 a
Out[44]:array([[10, 2, 3], [ 4, 5, 6]])
In [45]:a = np.array([[1,2,3,4,5],[6,7,8,9,10]], int)
In [47]:a
Out[47]:array([[ 1, 2, 3, 4, 5], [ 6, 7, 8, 9, 10]])
In [51]:# a[row,column] a[:, 2:]
Out[51]:array([[ 3, 4, 5], [ 8, 9, 10]])
In [48]:a[1, 1:3]
Out[48]:array([7, 8])
In [49]:a[1:3] # 1 Row ~ 2 Row 전체
Out[49]:array([[ 6, 7, 8, 9, 10]])
In [54]:test_example = np.array([[1,2,5,8], [1,2,5,8], [1,2,5,8], [1,2,5,8]])
In [55]:test_example[1:2, :2]
Out[55]:array([[1, 2]])
In [56]:a = np.arange(100).reshape(10, 10) a
Out[56]:array([[ 0, 1, 2, 3, 4, 5, 6, 7, 8, 9], [10, 11, 12, 13, 14, 15, 16, 17, 18, 19], [20, 21, 22, 23, 24, 25, 26, 27, 28, 29], [30, 31, 32, 33, 34, 35, 36, 37, 38, 39], [40, 41, 42, 43, 44, 45, 46, 47, 48, 49], [50, 51, 52, 53, 54, 55, 56, 57, 58, 59], [60, 61, 62, 63, 64, 65, 66, 67, 68, 69], [70, 71, 72, 73, 74, 75, 76, 77, 78, 79], [80, 81, 82, 83, 84, 85, 86, 87, 88, 89], [90, 91, 92, 93, 94, 95, 96, 97, 98, 99]])
In [57]:a[:,-1]
Out[57]:array([ 9, 19, 29, 39, 49, 59, 69, 79, 89, 99])
In [58]:a[:,::2] # a[row,::2] 여기서 2는 간격을 의미 전체 row에서 2칸씩 간격을 두고 가져오기
Out[58]:array([[ 0, 2, 4, 6, 8], [10, 12, 14, 16, 18], [20, 22, 24, 26, 28], [30, 32, 34, 36, 38], [40, 42, 44, 46, 48], [50, 52, 54, 56, 58], [60, 62, 64, 66, 68], [70, 72, 74, 76, 78], [80, 82, 84, 86, 88], [90, 92, 94, 96, 98]])
In [59]:a[::2,::3] # row와 column에서 2칸 3칸씩 띄어서 가져와라.
Out[59]:array([[ 0, 3, 6, 9], [20, 23, 26, 29], [40, 43, 46, 49], [60, 63, 66, 69], [80, 83, 86, 89]])
creation function¶
arange : array의 범위를 지정하여, 값의 list를 생성하는 명령어
In [60]:np.arange(0, 5, 0.5) # 시작, 끝, step 여기서는 step이 float 단위도 가능
Out[60]:array([0. , 0.5, 1. , 1.5, 2. , 2.5, 3. , 3.5, 4. , 4.5])
In [61]:np.arange(30).reshape(5,6)
Out[61]:array([[ 0, 1, 2, 3, 4, 5], [ 6, 7, 8, 9, 10, 11], [12, 13, 14, 15, 16, 17], [18, 19, 20, 21, 22, 23], [24, 25, 26, 27, 28, 29]])
ones, zeros & empty¶
In [62]:np.zeros(shape=(10,), dtype=np.int8) # 10 - zero vector 생성
Out[62]:array([0, 0, 0, 0, 0, 0, 0, 0, 0, 0], dtype=int8)
- empty : shape만 주어지고 비어있는 ndarray 생성(메모리 초기화를 안하고 잡기만 함)
In [71]:np.empty(shape=(10,), dtype=np.int8)
Out[71]:array([ 16, 64, 71, -47, 32, 2, 0, 0, 0, 0], dtype=int8)
In [72]:np.empty((3,5))
Out[72]:array([[0., 0., 0., 0., 0.], [0., 0., 0., 0., 0.], [0., 0., 0., 0., 0.]])
- something_like : 기존 ndarray의 shape 크기 만큼 1,0 또는 empty array를 반환
In [67]:test_matrix = np.arange(30).reshape(5,6) np.ones_like(test_matrix)
Out[67]:array([[1, 1, 1, 1, 1, 1], [1, 1, 1, 1, 1, 1], [1, 1, 1, 1, 1, 1], [1, 1, 1, 1, 1, 1], [1, 1, 1, 1, 1, 1]])
In [76]:np.zeros_like(test_matrix, dtype=np.float32)
Out[76]:array([[0., 0., 0., 0., 0., 0.], [0., 0., 0., 0., 0., 0.], [0., 0., 0., 0., 0., 0.], [0., 0., 0., 0., 0., 0.], [0., 0., 0., 0., 0., 0.]], dtype=float32)
- identity : 단위행렬을 생성
In [77]:np.identity(n=3, dtype=np.int8)
Out[77]:array([[1, 0, 0], [0, 1, 0], [0, 0, 1]], dtype=int8)
In [78]:np.identity(5)
Out[78]:array([[1., 0., 0., 0., 0.], [0., 1., 0., 0., 0.], [0., 0., 1., 0., 0.], [0., 0., 0., 1., 0.], [0., 0., 0., 0., 1.]])
- eye : 대각선이 1인 행렬, k값으로 시작 index 변경 가능
In [79]:np.eye(3)
Out[79]:array([[1., 0., 0.], [0., 1., 0.], [0., 0., 1.]])
In [80]:np.eye(3,5, k=2)
Out[80]:array([[0., 0., 1., 0., 0.], [0., 0., 0., 1., 0.], [0., 0., 0., 0., 1.]])
In [81]:np.eye(N=3, M=5, dtype=np.int8)
Out[81]:array([[1, 0, 0, 0, 0], [0, 1, 0, 0, 0], [0, 0, 1, 0, 0]], dtype=int8)
- diag : 대각 행렬의 값을 추출함
In [83]:matrix = np.arange(9).reshape(3,3) np.diag(matrix)
Out[83]:array([0, 4, 8])
In [84]:matrix
Out[84]:array([[0, 1, 2], [3, 4, 5], [6, 7, 8]])
In [85]:np.diag(matrix, k=1) # k : start index
Out[85]:array([1, 5])
- random sampling
In [86]:np.random.uniform(0,1,10).reshape(2,5) # 균등분포
Out[86]:array([[0.04930505, 0.17615164, 0.45059564, 0.39798379, 0.83080475], [0.74717455, 0.21242604, 0.14465865, 0.71801057, 0.34285649]])
In [87]:np.random.normal(0,1,10).reshape(2,5) # 정규분포
Out[87]:array([[-0.7412961 , -0.90824221, -0.06546223, 0.24561681, 0.25712025], [ 0.34237267, -0.69988476, 1.30544954, -1.28016773, -1.26866744]])
Operation function¶
- sum
In [88]:test_array = np.arange(1,11) test_array
Out[88]:array([ 1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
In [89]:test_array.sum()
Out[89]:55
In [90]:sum(test_array)
Out[90]:55
- axis : 모든 operation function을 실행할 때 기준이 되는 dimension 축
In [2]:test_array = np.arange(1,13).reshape(3,4) test_array
Out[2]:array([[ 1, 2, 3, 4], [ 5, 6, 7, 8], [ 9, 10, 11, 12]])
shape 기준으로 axis는 앞에서부터 세고, rank는 뒤에서부터 센다.
- 새롭게 생성된 축이 axis = 0 이 된다.
In [3]:test_array.sum(axis=1), test_array.sum(axis=0)
Out[3]:(array([10, 26, 42]), array([15, 18, 21, 24]))
mean, std , var 등 통계 계산도 가능
In [5]:test_array.mean(axis=1)
Out[5]:array([ 2.5, 6.5, 10.5])
In [6]:test_array.std(axis=1)
Out[6]:array([1.11803399, 1.11803399, 1.11803399])
In [7]:np.sqrt(test_array)
Out[7]:array([[1. , 1.41421356, 1.73205081, 2. ], [2.23606798, 2.44948974, 2.64575131, 2.82842712], [3. , 3.16227766, 3.31662479, 3.46410162]])
In [8]:np.exp(test_array)
Out[8]:array([[2.71828183e+00, 7.38905610e+00, 2.00855369e+01, 5.45981500e+01], [1.48413159e+02, 4.03428793e+02, 1.09663316e+03, 2.98095799e+03], [8.10308393e+03, 2.20264658e+04, 5.98741417e+04, 1.62754791e+05]])
concatenate¶
numpy array를 합치는(붙이는) 함수
vstack , hstack
In [9]:# vertical stack a = np.array([1,2,3]) b = np.array([2,3,4]) np.vstack((a,b))
Out[9]:array([[1, 2, 3], [2, 3, 4]])
In [10]:# horizontal stack a = np.array([[1],[2],[3]]) b = np.array([[2],[3],[4]]) np.hstack((a,b))
Out[10]:array([[1, 2], [2, 3], [3, 4]])
In [12]:a = np.array([[1,2,3]]) b = np.array([[2,3,4]]) np.concatenate((a,b), axis=0)
Out[12]:array([[1, 2, 3], [2, 3, 4]])
In [13]:a = np.array([[1,2],[3,4]]) b = np.array([[5],[6]]) np.concatenate((a,b), axis=1)
Out[13]:array([[1, 2, 5], [3, 4, 6]])
In [14]:a = np.array([[1,2],[3,4]]) b = np.array([5,6])
In [15]:b.shape
Out[15]:(2,)
- np.newaxis : 축을 하나 추가
In [16]:b = b[np.newaxis, :] b
Out[16]:array([[5, 6]])
In [17]:np.concatenate((a, b.T), axis=1)
Out[17]:array([[1, 2, 5], [3, 4, 6]])
Operation b/t arrays¶
numpy는 array간의 기본적인 사칙연산을 지원함
In [18]:test_a = np.array([[1,2,3],[4,5,6]], float)
In [19]:test_a + test_a
Out[19]:array([[ 2., 4., 6.], [ 8., 10., 12.]])
- Elment-wise operations : array간 shape이 같을때 일어나는 연산
In [21]:test_a * test_a
Out[21]:array([[ 1., 4., 9.], [16., 25., 36.]])
- Dot product : Matrix의 기본연산
In [26]:test_a = np.arange(1,7).reshape(2,3) test_b = np.arange(7,13).reshape(3,2)
In [27]:test_b
Out[27]:array([[ 7, 8], [ 9, 10], [11, 12]])
In [28]:test_a.dot(test_b)
Out[28]:array([[ 58, 64], [139, 154]])
- transpose
In [29]:test_a = np.arange(1,7).reshape(2,3) test_a
Out[29]:array([[1, 2, 3], [4, 5, 6]])
In [30]:test_a.transpose()
Out[30]:array([[1, 4], [2, 5], [3, 6]])
In [31]:test_a.T
Out[31]:array([[1, 4], [2, 5], [3, 6]])
- broadcasting : Shape이 다른 배열 간 연산을 지원하는 기능
In [32]:test_matrix = np.array([[1,2,3],[4,5,6]], float) scalar = 3
In [33]:test_matrix + scalar
Out[33]:array([[4., 5., 6.], [7., 8., 9.]])
In [34]:# matrix와 vector의 연산 test_matrix = np.arange(1,13).reshape(4,3) test_vector = np.arange(10,40,10) test_matrix + test_vector
Out[34]:array([[11, 22, 33], [14, 25, 36], [17, 28, 39], [20, 31, 42]])
numpy performance¶
- timeit : jupyter 환경에서 코드의 퍼포먼스를 체크하는 함수
In [35]:def scalar_vector_product(scalar, vector): result = [] for value in vector: result.append(scalar * value) return result iternation_max = 10000000 vector = list(range(iternation_max)) scalar = 2 #%timeit scalar_vector_product(scalar, vector) # for loop을 이용한 성능
908 ms ± 18.4 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)
In [ ]:#%timeit [scalar * vector for value in range(iternation_max)]
In [ ]:#%timeit np.arange(iternation_max) * scalar
In [3]:a = np.arange(10) a
Out[3]:array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9])
In [4]:a < 4
Out[4]:array([ True, True, True, True, False, False, False, False, False, False])
In [5]:a < 1
Out[5]:array([ True, False, False, False, False, False, False, False, False, False])
In [6]:np.all(a < 10)
Out[6]:True
In [8]:np.any(a > 5)
Out[8]:True
In [9]:test_a = np.array([1, 3, 0], float) test_b = np.array([5, 2, 1], float) test_a > test_b
Out[9]:array([False, True, False])
In [10]:test_a == test_b
Out[10]:array([False, False, False])
In [11]:a = np.array([1, 3, 0], float) np.logical_and(a > 0, a < 3) # and 조건의 condition
Out[11]:array([ True, False, False])
In [12]:b = np.array([True, False, True], bool) np.logical_not(b) # NOT 조건의 Condition
Out[12]:array([False, True, False])
In [13]:c = np.array([False, True, False], bool) np.logical_or(b, c) # OR 조건의 condition
Out[13]:array([ True, True, True])
- np.where : where 조건
In [14]:np.where(a > 0, 3, 2) # where(condition, TRUE, FALSE)
Out[14]:array([3, 3, 2])
In [20]:a = np.array([1,3,0]) np.where(a>2)
Out[20]:(array([1], dtype=int64),)
In [16]:a = np.arange(10) np.where(a>5) # Index 값 반환
Out[16]:(array([6, 7, 8, 9], dtype=int64),)
In [18]:a = np.array([1, np.NaN, np.Inf], float) np.isnan(a)
Out[18]:array([False, True, False])
In [19]:np.isfinite(a) # is finite number
Out[19]:array([ True, False, False])
- argmax & argmin : array내 최대값 또는 최소값의 index를 반환
In [25]:a = np.array([1,2,3,4,5,8,78,23,3]) np.argmax(a), np.argmin(a)
Out[25]:(6, 0)
In [26]:a.argsort() # 작은 값부터 index로 뽑기
Out[26]:array([0, 1, 2, 8, 3, 4, 5, 7, 6], dtype=int64)
In [27]:a.argsort()[::-1]
Out[27]:array([6, 7, 5, 4, 3, 8, 2, 1, 0], dtype=int64)
In [28]:a[np.argmin(a)] # a의 가장 작은 값
Out[28]:1
In [23]:a = np.array([[1,2,4,7],[9,88,6,45],[9,76,3,4]]) np.argmax(a, axis=1) , np.argmin(a, axis=0)
Out[23]:(array([3, 1, 1], dtype=int64), array([0, 0, 2, 2], dtype=int64))
Boolean & fancy index¶
특정 조건에 따른 값을 배열 형태로 추출
Boolean Index
In [29]:test_array = np.array([1, 4, 0, 2, 3, 8, 9, 7], float) test_array > 3
Out[29]:array([False, True, False, False, False, True, True, True])
In [30]:test_array[test_array > 3] # 조건이 True인 index의 element만 추출
Out[30]:array([4., 8., 9., 7.])
In [31]:test_array.shape
Out[31]:(8,)
In [32]:(test_array > 3).shape
Out[32]:(8,)
fancy index
In [33]:a = np.array([2,4,6,8], float) b = np.array([0,0,1,3,1], int) # index 값, 반드시 integer로 선언 a[b]
Out[33]:array([2., 2., 4., 8., 4.])
In [34]:a.take(b) # take 함수 : bracket index와 같은 효과
Out[34]:array([2., 2., 4., 8., 4.])
In [35]:a = np.array([[1, 4], [9, 16]], float) b = np.array([0, 0, 1, 1, 0], int) c = np.array([0, 1, 1, 1, 1], int) a[b,c] # b를 row index, c를 column index로 변환하여 표시
Out[35]:array([ 1., 4., 16., 16., 4.])
In [36]:a[b] # row 값만 넣는 경우
Out[36]:array([[ 1., 4.], [ 1., 4.], [ 9., 16.], [ 9., 16.], [ 1., 4.]])
numpy data i/o¶
- loadtxt & savetxt : text type 데이터를 읽고 저장하는 기능
In [40]:a = np.loadtxt('populations.txt', delimiter="\t")
In [41]:a[:10]
Out[41]:array([[ 1900., 30000., 4000., 48300.], [ 1901., 47200., 6100., 48200.], [ 1902., 70200., 9800., 41500.], [ 1903., 77400., 35200., 38200.], [ 1904., 36300., 59400., 40600.], [ 1905., 20600., 41700., 39800.], [ 1906., 18100., 19000., 38600.], [ 1907., 21400., 13000., 42300.], [ 1908., 22000., 8300., 44500.], [ 1909., 25400., 9100., 42100.]])
In [43]:a_int = a.astype(int) a_int_3 = a_int[:3]
In [45]:np.savetxt("int_data_2.csv", a_int_3, fmt='%.2e', delimiter=",")
numpy object - npy¶
In [49]:np.save("npy_test.npy", arr=a_int_3) # pikle로 저장
In [50]:a_test = np.load(file="npy_test.npy") a_test
Out[50]:array([[ 1900, 30000, 4000, 48300], [ 1901, 47200, 6100, 48200], [ 1902, 70200, 9800, 41500]])
In [ ]:'인공지능 > 부스트캠프 Ai Tech' 카테고리의 다른 글
[python]6. pandas_2 (0) 2022.01.21 [python]6. pandas_1 (0) 2022.01.21 [python]4. Python Data Handling (0) 2022.01.21 [python]3. Exception_File_LogHandling (0) 2022.01.21 [python]0. Pythonic code (0) 2022.01.21