뉴비에욤
PyTorch 튜토리얼 6 - 텐서 본문
2017/07/13 - [Machine Learning/PyTorch] - 윈도우 10 PyTorch 환경 구성 - 설치
2018/04/30 - [Machine Learning/PyTorch] - PyTorch 튜토리얼 1 - PyTorch란?
2018/04/30 - [Machine Learning/PyTorch] - PyTorch 튜토리얼 2 - Autograd : 자동 미분
2018/05/01 - [Machine Learning/PyTorch] - PyTorch 튜토리얼 3 - 뉴럴 네트워크(신경망)
2018/05/01 - [Machine Learning/PyTorch] - PyTorch 튜토리얼 4 - Classifier 학습
2018/05/01 - [Machine Learning/PyTorch] - PyTorch 튜토리얼 5 - 데이터 병렬 처리
원문 : http://pytorch.org/tutorials/beginner/former_torchies/tensor_tutorial.html
* 17년도 07월에 초번 번역 후, 파이토치 최신 버전인 0.4.0에 맞추어 갱신 된 번역본
* 최근 갱신일 : 2018-05-01
목 차 ( 초보자 튜토리얼 )
B. Torch 사용자를 위한 PyTorch
6. 텐서
- 인-플레이스 / 아웃-플레이스
- 0-인덱싱
- 카멜 표기법 없음
- NumPy 변환
- torch 텐서 -> numpy 배열로 변환
- numpy 배열 -> torch 텐서로 변환
- CUDA 텐서
텐서(Tensors)
파이토치에서의 텐서는 토치에서의 텐서와 거의 동일하게 동작한다.
초기화 되지 않은 5*7 크기의 텐서를 만든다.
- 소스
import torch
a = torch.empty(5, 7, dtype=torch.float)
mean(평균) = 0, var(분산) = 1을 가지는 정규 분포로 랜덤화 된 이중 텐서를 초기화 한다.
- 소스
a = torch.randn(5, 7, dtype=torch.double)
print(a)
print(a.size())
- 결과
tensor([[ 0.2095, -1.5431, -0.1285, -0.3743, -0.4776, -0.4502, 0.6279],
[ 0.9514, -1.7334, -0.6382, -0.3209, -0.2505, -1.1160, -1.0959],
[-0.3199, 1.7155, 1.3164, -0.3394, -0.2693, -1.9001, 0.6337],
[-0.2756, -1.3569, -0.2064, 2.4318, -1.1204, -0.8584, 0.1493],
[-0.5671, 0.9556, 0.5539, 0.0953, 0.6315, -1.2639, 0.3836]], dtype=torch.float64)
torch.Size([5, 7])
torch.Size는 파이썬의 튜플 자료형이기 때문에 튜플 연산을 그대로 사용할 수 있다.
인-플레이스(Inplace) / 아웃-플레이스(Out-of-place)
첫 번째 차이점은 텐서의 모든 인-플레이스 연산은 _를 postfix 방식으로 표시한다는 점이다. 예를 들어, add는 아웃-플레이스 연산을 하고, add_는 인-플레이스 연산을 한다.
- 소스
a.fill_(3.5)
# a has now been filled with the value 3.5
b = a.add(4.0)
# a is still filled with 3.5
# new tensor b is returned with values 3.5 + 4.0 = 7.5
print(a, b)
- 결과
tensor([[ 3.5000, 3.5000, 3.5000, 3.5000, 3.5000, 3.5000, 3.5000],
[ 3.5000, 3.5000, 3.5000, 3.5000, 3.5000, 3.5000, 3.5000],
[ 3.5000, 3.5000, 3.5000, 3.5000, 3.5000, 3.5000, 3.5000],
[ 3.5000, 3.5000, 3.5000, 3.5000, 3.5000, 3.5000, 3.5000],
[ 3.5000, 3.5000, 3.5000, 3.5000, 3.5000, 3.5000, 3.5000]], dtype=torch.float64) tensor([[ 7.5000, 7.5000, 7.5000, 7.5000, 7.5000, 7.5000, 7.5000],
[ 7.5000, 7.5000, 7.5000, 7.5000, 7.5000, 7.5000, 7.5000],
[ 7.5000, 7.5000, 7.5000, 7.5000, 7.5000, 7.5000, 7.5000],
[ 7.5000, 7.5000, 7.5000, 7.5000, 7.5000, 7.5000, 7.5000],
[ 7.5000, 7.5000, 7.5000, 7.5000, 7.5000, 7.5000, 7.5000]], dtype=torch.float64)
narrow처럼 일부 연산은 인-플레이스 형태가 없기 때문에 .narrow_는 존재하지 않는 연산이다. 또한 fill_과 같은 일부 연산은 아웃-플레이스 형태가 없기 때문에 .fill는 존재하지 않는 연산이 된다.
또 다른 차이점은 텐서는 0-인덱스라는 것이다. lua에서 텐서는 1-인덱스이다. 2
- 소스
b = a[0, 3] # select 1st row, 4th column from a
또한 텐서는 파이썬의 슬라이싱을 이용하여 인덱스가 가능하다.
- 소스
b = a[:, 3:5] # selects all rows, 4th column and 5th column from a
카멜 표기법 없음(No camel casing)
이 외에도 카멜 표기법을 사용하지 않는다는 소소한 차이점도 있다. 예를 들어 indexAdd는 index_add_가 된다.
카멜표기법이란?
- 단봉 낙타 표기법이라고도 함
- 각 단어의 첫 문자를 대문자로 표기하고 붙여쓰되, 맨처음 문자는 소문자로 표기
- 띄어쓰기 대신 대문자로 단어를 구분
- 예시: backgroundColor, typeName, iPhone
출처 : https://goo.gl/2D5sgN
- 소스
x = torch.ones(5, 5)
print(x)
- 결과
tensor([[ 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.]])
- 소스
z = torch.empty(5, 2)
z[:, 0] = 10
z[:, 1] = 100
print(z)
- 결과
tensor([[ 10., 100.],
[ 10., 100.],
[ 10., 100.],
[ 10., 100.],
[ 10., 100.]])
- 소스
x.index_add_(1, torch.tensor([4, 0], dtype=torch.long), z)
print(x)
- 결과
tensor([[ 101., 1., 1., 1., 11.],
[ 101., 1., 1., 1., 11.],
[ 101., 1., 1., 1., 11.],
[ 101., 1., 1., 1., 11.],
[ 101., 1., 1., 1., 11.]])
Numpy 변환 (Numpy Bridge)
torch 텐서를 numpy 배열로, 혹은 반대로 변환하는 것은 꽤 쉬운 작업이다. torch 텐서와 numpy 배열은 기본적인 저장 공간(메모리 공간)를 공유하기 때문에 하나를 변경하면 다른 하나도 자동으로 변경 된다.
torch 텐서 -> numpy 배열로 변환 ( Converting torch Tensor to numpy Array)
- 소스
a = torch.ones(5)
print(a)
- 결과
tensor([ 1., 1., 1., 1., 1.])
- 소스
b = a.numpy()
print(b)
- 결과
[1. 1. 1. 1. 1.]
- 소스
a.add_(1)
print(a)
print(b) # see how the numpy array changed in value
- 결과
tensor([ 2., 2., 2., 2., 2.])
[2. 2. 2. 2. 2.]
numpy 배열 -> torch 텐서로 변환 ( Converting numpy Array to torch Tensor)
- 소스
import numpy as np
a = np.ones(5)
b = torch.from_numpy(a)
np.add(a, 1, out=a)
print(a)
print(b) # see how changing the np array changed the torch Tensor automatically
- 결과
[2. 2. 2. 2. 2.]
tensor([ 2., 2., 2., 2., 2.], dtype=torch.float64)
CharTensor를 제외한 CPU의 모든 텐서는 NumPy로 변환할 수 있고, 그 반대의 경우(numpy->텐서)도 가능하다.
CUDA 텐서 ( CUDA Tensors )
CUDA 텐서는 pytorch에서 손쉽게 사용할 수 있으며, CUDA 텐서를 CPU에서 GPU로 옮겨도 기본 형태(underlying type)는 유지 된다.
- 소스
# let us run this cell only if CUDA is available
if torch.cuda.is_available():
# creates a LongTensor and transfers it
# to GPU as torch.cuda.LongTensor
a = torch.full((10,), 3, device=torch.device("cuda"))
print(type(a))
b = a.to(torch.device("cpu"))
# transfers it to CPU, back to
# being a torch.LongTensor
- 결과
< class 'torch.Tensor'>
'Machine Learning > PyTorch' 카테고리의 다른 글
PyTorch 튜토리얼 8 - nn 패키지 (0) | 2018.05.02 |
---|---|
PyTorch 튜토리얼 7 - Autograd (2) | 2018.05.02 |
PyTorch 튜토리얼 5 - 데이터 병렬 처리 (1) | 2018.05.01 |
PyTorch 튜토리얼 4 - 분류기(classifier) 학습 (1) | 2018.05.01 |
PyTorch 튜토리얼 3 - 뉴럴 네트워크(신경망, Neural Networks) (3) | 2018.05.01 |