<SYSTEM_TASK:>
Given the following text description, write Python code to implement the functionality described below step by step
<END_TASK>
<USER_TASK:>
Description:
 PyTorch Implementation
Simple version
가장 일반적인 파이토치 구현 방법으로 케라스된 예제 1-1을 변환한다.
Step1:  Detail version with monitoring variables
파이토치로 변환된 코드가 제대로 동작하는지 중간 중간을 모니터링 한다.
Step2:  Compatible version
케라스에서 사용한 코드를 최대한 고치지 않고 사용하는 방법이다. 모델 클래스를 작성할 때 입력에 대해 부가적인 처리를 함으로 나머지 코드는 케라스 경우와 비슷하게 사용할 수 있다. 먼저 forward(.)에서 Numpy의 어레이 입력을 토치 어레이로 바꾸는 과정을 포함한다. 그리고 앞선 Simple version에서 모델을 학습하는 코드를 fit()라는 모델 클래스 함수를 만들어 처리하도록 해 주었다. 그러고 나면 실제 수행코드는 케라스의 경우와 매우 유사하게 작성이 가능함을 알 수 있다.
Step3:  GPU Version
GPU 버전으로 파이토치 코드를 작성할 경우는 model.to(device), x.to(device), y.to(device)라는 세가지 과정이 필요하다. 아래 코드는 예제 1-1을 파이토치 코드로 바꾼 뒤에 타켓 프로세서에 맞게 돌도로 디바이스가 CPU인지 GPU인지를 검사하여 해당 프로세서에 맞게 동작하게 만드는 코드이다.
Step4:  GPU인지 CPU인지 검사
프로세서로 GPU를 사용하는 있는지 아닌지를 검사하고 device 변수에 프로세서 타입을 적어넣는다.
<ASSISTANT_TASK:>
Python Code:
import torch
import numpy as np
x = np.array([0, 1, 2, 3, 4]).astype('float32').reshape(-1,1) 
y = x * 2 + 1
class Model(torch.nn.Module):
    def __init__(self):
        super(Model,self).__init__()
        self.layer = torch.nn.Linear(1,1)
    def forward(self, x):
        return self.layer(x)
model = Model()
Optimizer = torch.optim.SGD(model.parameters(), lr=0.01)
for epoch in range(1000):
    x_tr = torch.from_numpy(x[:2,:1]).type(torch.FloatTensor)
    y_tr = torch.from_numpy(y[:2,:1]).type(torch.FloatTensor)
    y_pr = model(x_tr)
    loss = torch.pow(torch.abs(y_tr - y_pr),2)
    Optimizer.zero_grad()
    torch.sum(loss).backward()
    Optimizer.step()
print(model(torch.from_numpy(x).type(torch.FloatTensor)).detach().numpy())
Explanation: PyTorch Implementation
Simple version
가장 일반적인 파이토치 구현 방법으로 케라스된 예제 1-1을 변환한다.
End of explanation
import torch
import numpy as np
x = np.array([0, 1, 2, 3, 4]).astype('float32').reshape(-1,1) 
y = x * 2 + 1
class Model(torch.nn.Module):
    def __init__(self):
        super(Model,self).__init__()
        self.layer = torch.nn.Linear(1,1)
    def forward(self, x):
        return self.layer(x)
model = Model()
Optimizer = torch.optim.SGD(model.parameters(), lr=0.01)
print('w=', list(model.parameters())[0].detach().numpy())
print('b=', list(model.parameters())[1].detach().numpy())
print()
for epoch in range(1000):
    x_tr = torch.from_numpy(x[:2,:1]).type(torch.FloatTensor)
    y_tr = torch.from_numpy(y[:2,:1]).type(torch.FloatTensor)
    y_pr = model(x_tr)
    loss = torch.pow(torch.abs(y_tr - y_pr),2)
    if epoch < 3:
        print(f'Epoch:{epoch}')
        print('y_pr:', y_pr.detach().numpy())
        print('y_tr:', y[:2,:1])
        print('loss:', loss.detach().numpy())
        print()
    Optimizer.zero_grad()
    torch.sum(loss).backward()
    Optimizer.step()
print(model(torch.from_numpy(x).type(torch.FloatTensor)).detach().numpy())
Explanation: Detail version with monitoring variables
파이토치로 변환된 코드가 제대로 동작하는지 중간 중간을 모니터링 한다.
End of explanation
import torch
import numpy as np
x = np.array([0, 1, 2, 3, 4]).astype('float32').reshape(-1,1) 
y = x * 2 + 1
class Model(torch.nn.Module):
    def __init__(self):
        super(Model,self).__init__()
        self.layer = torch.nn.Linear(1,1)
        self.Optimizer = torch.optim.SGD(self.parameters(), lr=0.01)
    def forward(self, x):
        x = torch.from_numpy(x).type(torch.FloatTensor)
        return self.layer(x)
    def fit(self, x, y, epochs):
        for epoch in range(epochs):
            y_tr = torch.from_numpy(y).type(torch.FloatTensor)
            y_pr = model(x)
            loss = torch.pow(torch.abs(y_tr - y_pr),2)
            self.Optimizer.zero_grad()
            torch.sum(loss).backward()
            self.Optimizer.step()
model = Model()
model.fit(x[:2], y[:2], epochs=1000)
print(model(x))
Explanation: Compatible version
케라스에서 사용한 코드를 최대한 고치지 않고 사용하는 방법이다. 모델 클래스를 작성할 때 입력에 대해 부가적인 처리를 함으로 나머지 코드는 케라스 경우와 비슷하게 사용할 수 있다. 먼저 forward(.)에서 Numpy의 어레이 입력을 토치 어레이로 바꾸는 과정을 포함한다. 그리고 앞선 Simple version에서 모델을 학습하는 코드를 fit()라는 모델 클래스 함수를 만들어 처리하도록 해 주었다. 그러고 나면 실제 수행코드는 케라스의 경우와 매우 유사하게 작성이 가능함을 알 수 있다.
End of explanation
import torch
import numpy as np
Explanation: GPU Version
GPU 버전으로 파이토치 코드를 작성할 경우는 model.to(device), x.to(device), y.to(device)라는 세가지 과정이 필요하다. 아래 코드는 예제 1-1을 파이토치 코드로 바꾼 뒤에 타켓 프로세서에 맞게 돌도로 디바이스가 CPU인지 GPU인지를 검사하여 해당 프로세서에 맞게 동작하게 만드는 코드이다.
End of explanation
if torch.cuda.is_available():
    device = torch.device('cuda')
else:
    device = torch.device('cpu')
    
print('Using PyTorch version:', torch.__version__, ' Device:', device)
x = np.array([0, 1, 2, 3, 4]).astype('float32').reshape(-1,1) 
y = x * 2 + 1
class Model(torch.nn.Module):
    def __init__(self):
        super(Model,self).__init__()
        self.layer = torch.nn.Linear(1,1)
        self.Optimizer = torch.optim.SGD(self.parameters(), lr=0.01)
    def forward(self, x):
        x = torch.from_numpy(x).type(torch.FloatTensor).to(device)
        return self.layer(x)
    def fit(self, x, y, epochs):
        for epoch in range(epochs):
            y_tr = torch.from_numpy(y).type(torch.FloatTensor).to(device)
            y_pr = model(x)
            loss = torch.pow(torch.abs(y_tr - y_pr),2)
            self.Optimizer.zero_grad()
            torch.sum(loss).backward()
            self.Optimizer.step()
model = Model().to(device)
model.fit(x[:2], y[:2], epochs=1000)
print(model(x))
Explanation: GPU인지 CPU인지 검사
프로세서로 GPU를 사용하는 있는지 아닌지를 검사하고 device 변수에 프로세서 타입을 적어넣는다.
End of explanation
<END_TASK>