728x90
반응형
[Numpy exercise 100] 1번 ~ 30번 문제풀이
[Numpy exercise 100] 31번 ~ 60번 문제풀이
[Numpy exercise 100] 61번 ~ 70번 문제풀이
[Numpy exercise 100] 71번 ~ 80번 문제풀이
https://github.com/rougier/numpy-100
81. Consider an array Z = [1,2,3,4,5,6,7,8,9,10,11,12,13,14], how to generate an array R = [[1,2,3,4], [2,3,4,5], [3,4,5,6], ..., [11,12,13,14]]? (★★★)
- 어레이 Z = [1,2,3,4,5,6,7,8,9,10,11,12,13,14], 어레이 R = [[1,2,3,4], [2,3,4,5], [3,4,5,6], ..., [11,12,13,14]]를 생성하는 방법을 고려하십시오.
- 1차원 벡터를 다차원 array로 reshape. 단, 원소 한칸씩 전진하며 쌓아가야 함
- stride_tricks.as_strided : 주어진 모양 및 보폭으로 배열을 만듦
from numpy.lib import stride_tricks
Z = np.arange(1,15,dtype=np.uint32)
R = stride_tricks.as_strided(Z,(11,4),(4,4)) # 최종 shape은 (11,4)가 되도록, 보폭은 (4,4)씩
print(R)
>>>
[[ 1 2 3 4]
[ 2 3 4 5]
[ 3 4 5 6]
[ 4 5 6 7]
[ 5 6 7 8]
[ 6 7 8 9]
[ 7 8 9 10]
[ 8 9 10 11]
[ 9 10 11 12]
[10 11 12 13]
[11 12 13 14]]
82. Compute a matrix rank (★★★)
- 행렬 순위를 계산합니다
- 문제가 잘 이해는 안되지만... 특이값 분해(Singular Value Decomposition, SVD)를 사용하여 행렬을 대각화한다.
- 특이값분해 설명 블로그(다크 프로그래머 님) : https://darkpgmr.tistory.com/106
Z = np.random.uniform(0,1,(10,10))
U, S, V = np.linalg.svd(Z) # Singular Value Decomposition
rank = np.sum(S > 1e-10)
print(rank)
# 또 다른 방법
rank = np.linalg.matrix_rank(Z)
print(rank)
>>>
10
83. How to find the most frequent value in an array?
- 배열에서 가장 빈번한 값을 찾는 방법은 무엇입니까?
- np.bincount()를 통해서 각 값을 count한 뒤, argmax()로 가장 큰 값을 찾아냄
- argmax() : f(x)의 최대값을 만들어주는 입력 x 자체를 뜻함 (인덱스 반환)
Z = np.random.randint(0,10,50)
print(np.bincount(Z).argmax())
>>>
6
84. Extract all the contiguous 3x3 blocks from a random 10x10 matrix (★★★)
- 랜덤 10x10 행렬에서 모든 연속 3x3 블럭 추출
Z = np.random.randint(0,5,(10,10))
n = 3
i = 1 + (Z.shape[0]-3)
j = 1 + (Z.shape[1]-3)
C = stride_tricks.as_strided(Z, shape=(i, j, n, n), strides=Z.strides + Z.strides)
print(C)
>>>
[[[[1 1 1]
[4 2 0]
[4 4 4]]
[[1 1 3]
[2 0 2]
[4 4 3]]
[[1 3 2]
[0 2 0]
[4 3 3]]
...
[[4 4 2]
[4 4 4]
[3 2 4]]]]
85. Create a 2D array subclass such that Z[i,j] == Z[j,i] (★★★)
- Z[i,j] == Z[j,i]와 같은 2D 배열 하위 클래스 만들기
class Symetric(np.ndarray):
def __setitem__(self, index, value):
i,j = index
super(Symetric, self).__setitem__((i,j), value)
super(Symetric, self).__setitem__((j,i), value)
def symetric(Z):
return np.asarray(Z + Z.T - np.diag(Z.diagonal())).view(Symetric)
S = symetric(np.random.randint(0, 10, (5,5)))
S[2,3] = 42
print(S)
>>>
[[ 1 9 14 12 0]
[ 9 9 10 11 5]
[14 10 1 42 6]
[12 11 42 3 6]
[ 0 5 6 6 7]]
86. Consider a set of p matrices wich shape (n,n) and a set of p vectors with shape (n,1). How to compute the sum of of the p matrix products at once? (result has shape (n,1)) (★★★)
- 형상(n,n)이 있는 p 행렬 집합과 형상(n,1)이 있는 p 벡터 집합을 고려하십시오. p 매트릭스 제품의 합계를 한 번에 계산하는 방법은 무엇입니까? (결과에 모양(n,1)이 있음)
- np.tensordot() 공식문서 : https://numpy.org/doc/stable/reference/generated/numpy.tensordot.html
p, n = 10, 20
M = np.ones((p,n,n))
V = np.ones((p,n,1))
S = np.tensordot(M, V, axes=[[0, 2], [0, 1]]) # np.tensordot(a, b, 축) : 지정된 축에 따라 텐서 곱을 계산
print(S)
# 추가설명... (설명해주실 분 계시면 댓글 부탁드리겠습니다ㅜㅜ)
# It works, because:
# M is (p,n,n)
# V is (p,n,1)
# Thus, summing over the paired axes 0 and 0 (of M and V independently),
# and 2 and 1, to remain with a (n,1) vector.
>>>
[[200.]
[200.]
[200.]
[200.]
[200.]
[200.]
[200.]
[200.]
[200.]
[200.]
[200.]
[200.]
[200.]
[200.]
[200.]
[200.]
[200.]
[200.]
[200.]
[200.]]
87. Consider a 16x16 array, how to get the block-sum (block size is 4x4)? (★★★)
- 16x16 array가 주어질 때, 4x4의 블록합계로 결과값을 가져오는 방법
-
- np.add.reduceat() : 주어진 배열의 인덱스를 고려하여 해당인덱스부터 끝까지의 합계를 구해 배열로 반환
-
- stride_tricks.sliding_window_view()를 이용해 합계
-
Z = np.ones((16,16))
print(Z)
k = 4
S = np.add.reduceat(np.add.reduceat(Z, np.arange(0, Z.shape[0], k), axis=0),
np.arange(0, Z.shape[1], k), axis=1)
print(S)
>>>
# Z
[[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. 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. 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. 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. 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. 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. 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. 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.]
[1. 1. 1. 1. 1. 1. 1. 1. 1. 1. 1. 1. 1. 1. 1. 1.]]
# S
[[16. 16. 16. 16.]
[16. 16. 16. 16.]
[16. 16. 16. 16.]
[16. 16. 16. 16.]]
# sliding_window_view 사용
Z = np.ones((16,16))
k = 4
windows = np.lib.stride_tricks.sliding_window_view(Z, (k, k))
S = windows[::k, ::k, ...].sum(axis=(-2, -1))
print(S)
88. How to implement the Game of Life using numpy arrays? (★★★)
- numpy 배열을 사용하여 Game of Life를 구현하는 방법은 무엇입니까?
- Game of Life (라이프게임) 위키피디아(한글) : https://ko.wikipedia.org/wiki/%EB%9D%BC%EC%9D%B4%ED%94%84_%EA%B2%8C%EC%9E%84
def iterate(Z):
# Count neighbours
N = (Z[0:-2,0:-2] + Z[0:-2,1:-1] + Z[0:-2,2:] +
Z[1:-1,0:-2] + Z[1:-1,2:] +
Z[2: ,0:-2] + Z[2: ,1:-1] + Z[2: ,2:])
# Apply rules
birth = (N==3) & (Z[1:-1,1:-1]==0)
survive = ((N==2) | (N==3)) & (Z[1:-1,1:-1]==1)
Z[...] = 0
Z[1:-1,1:-1][birth | survive] = 1
return Z
Z = np.random.randint(0,2,(50,50))
for i in range(100): Z = iterate(Z)
print(Z)
>>>
[[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]
[0 0 0 ... 0 0 0]]
89. How to get the n largest values of an array (★★★)
- 배열의 최대값 n개를 가져오는 방법
- argsort()으로 오름차순 정렬 뒤 뒤에서 n개 가져오기 (arg가 붙으면 인덱스를 반환한다.)
- argpartition()로 배열 내 가장 작은값 (-Z로 파라미터를 주었기 때문에) n개를 찾고 인덱스 반환
Z = np.arange(10000)
np.random.shuffle(Z) # 원소 순서를 랜덤으로 섞음
n = 5
# 일반적인 방법 (전체를 sorting하므로 조금 느림)
print (Z[np.argsort(Z)[-n:]])
# 좀 더 빠른 방법 (일부만 sorting하므로)
print (Z[np.argpartition(-Z,n)[:n]])
>>>
[8178 4152 4340 ... 229 3725 3684]
[9995 9996 9997 9998 9999]
[9998 9999 9996 9997 9995]
90. Given an arbitrary number of vectors, build the cartesian product (every combinations of every item) (★★★)
- 임의의 수의 벡터가 주어지면 데카르트 곱(모든 항목의 모든 조합)을 작성합니다.
- 데카르트 곱(곱집합) : https://ko.wikipedia.org/wiki/%EA%B3%B1%EC%A7%91%ED%95%A9
def cartesian(arrays):
arrays = [np.asarray(a) for a in arrays]
shape = (len(x) for x in arrays)
ix = np.indices(shape, dtype=int)
ix = ix.reshape(len(arrays), -1).T
for n, arr in enumerate(arrays):
ix[:, n] = arrays[n][ix[:, n]]
return ix
print (cartesian(([1, 2, 3], [4, 5], [6, 7])))
>>>
[[1 4 6]
[1 4 7]
[1 5 6]
[1 5 7]
[2 4 6]
[2 4 7]
[2 5 6]
[2 5 7]
[3 4 6]
[3 4 7]
[3 5 6]
[3 5 7]]
728x90
'Minding's Programming > Numpy & Pandas' 카테고리의 다른 글
[Numpy Exercise 100] 91번 ~ 100번 문제풀이 (0) | 2022.01.03 |
---|---|
[Numpy exercise 100] 71번 ~ 80번 문제풀이 (0) | 2021.12.28 |
[Numpy exercise 100] 61번 ~ 70번 문제풀이 (0) | 2021.12.27 |
[Numpy exercise 100] 31번 ~ 60번 문제풀이 (0) | 2021.12.24 |
[Numpy exercise 100] 1번 ~ 30번 문제풀이 (0) | 2021.12.23 |