基于Pytorch的简单神经网络实现(fizzbuzz游戏)

一、win11 配置pytorch环境

参考步骤

1.1 清华镜像设置问题

conda config --add channels http://mirrors.tuna.tsinghua.edu.cn/anaconda/pkgs/free/
conda config --add channels http://mirrors.tuna.tsinghua.edu.cn/anaconda/pkgs/main/
conda config --set show_channel_urls yes
conda config --add channels http://mirrors.tuna.tsinghua.edu.cn/anaconda/cloud/pytorch/

https://改为http://

二、vscode与anaconda_cmd不一致问题

2.1 环境变量设置

C:\Users\pck\anaconda3\Lib
C:\Users\pck\anaconda3\Scripts
C:\Users\pck\anaconda3
C:\Users\pck\anaconda3\Library\bin

三、Python基础知识

3.1

def fizzbuzz_decoder(number, lebal):
    '''
    将计算机内部自定义的编码信息转成自然语言表示
    '''
    return [str(number), 'fizz', 'buzz', 'fizzbuzz'][lebal]

3.2

def test(number):
    print("数字 %d 的类别为:%s \n" %(number, fizzbuzz_decoder(number, fizzbuzz_encoder(number))))

3.3

def binary_encoder(number):
    '''
    number相当于数据集本身特征,这里将number编码为二进制形式,以表示更多特征
    '''
    NUM_DIGITS = 10
    return np.array([number >> d & 1 for d in range (NUM_DIGITS)][::-1])

3.4

if __name__ == '__main__':
    for i in range(1,16):
        test(i)

3.5

x_train = torch.Tensor([binary_encoder(number) for number in range(101, 1024)])

Python括号的区别

3.6

x_train[0:5,]
x_train[:5]
x_train[0:5,:]

3.7

class MyDataset(Data.Dataset):
    def __init__(self):
        pass
    def __getitem__(self, index):
        pass
    def __len__(self):
        pass


赋值一定要给到self

四、Pytorch基础知识

4.1

x_train = torch.Tensor([binary_encoder(number) for number in range(101, 1024)])

pytroch torch.Tensor函数

4.2

class MyDataset(Data.Dataset):
    def __init__(self):
        pass
    def __getitem__(self, index):
        pass
    def __len__(self):
        pass

继承pytorch类(函数重写)
类的继承

4.3

class MyModel(nn.Module):
    def __init__(self):
        super(MyModel, self).__init__()
        self.linear1 = nn.Linear(10, 64) # 线性层
        self.activation = nn.ReLU()
        self.linear2 = nn.Linear(64, 8)
        self.linear3 = nn.Linear(8, 4)

    def forward(self, x):
        
        output = self.linear1(x)  # [batch_size, 64]
        output = self.activation(output)  # [batch_size, 64]
        output = self.linear2(output)  # [batch_size, 8]
        output = self.linear3(output)  # [batch_size, 4]
        return output

model = MyModel()

4.4

device = torch.device('cuda' if torch.cuda.is_available() else 'cpu')

使用GPU训练,但是要注意数据集、模型在GPU的部署及下载,最终才能输出结果

4.5

iter(train_loader).next()

取出一个batch,可以后续打印

4.6

model = MyModel()
model.load_state_dict(torch.load('testmodel1'))

加载模型

4.7

torch.save(model.state_dict(), 'testmodel1')

保存模型

五、实现源代码

CPU

import torch
import numpy
import torch.nn as nn
import torch.optim as optim
import torch.nn.functional as F
import torch.utils.data as Data
from PIL import Image
import numpy as np

# device = torch.device('cuda' if torch.cuda.is_available() else 'cpu')


def number_determinate(number):
    '''
    只是实现了这么一个功能,却没理解这样做的含义
    '''
    if number % 15 == 0:
        return 3
    elif number % 5 == 0:
        return 2
    elif number % 3 == 0:
        return 1
    return 0


def fizzbuzz_encoder(number):
    '''
    把抽象的表述变为数字的过程成为编码
    '''
    # 'fizzbuzz'
    if number % 15 == 0:
        return 3
    # 'buzz'
    elif number % 5 == 0:
        return 2
    # 'fizz'
    elif number % 3 == 0:
        return 1
    # str(number)
    return 0

def fizzbuzz_decoder(number, lebal):
    '''
    将计算机内部自定义的编码信息转成自然语言表示
    '''
    return [str(number), 'fizz', 'buzz', 'fizzbuzz'][lebal]

def test(number):
    print("数字 %d 的类别为:%s \n" %(number, fizzbuzz_decoder(number, fizzbuzz_encoder(number))))

def binary_encoder(number):
    '''
    number相当于数据集本身特征,这里将number编码为二进制形式,以表示更多特征
    '''
    NUM_DIGITS = 10
    return np.array([number >> d & 1 for d in range (NUM_DIGITS)][::-1])

x_train = torch.Tensor([binary_encoder(number) for number in range(101, 1024)])
y_train = torch.LongTensor([fizzbuzz_encoder(number) for number in range(101, 1024)])


class MyDataset(Data.Dataset):
    '''
    先定义(继承)类(函数重写)
    '''
    def __init__(self, x_train, y_train):
        self.x_train = x_train
        self.y_train = y_train
    def __getitem__(self, index):
        return self.x_train[index], self.y_train[index]
    def __len__(self):
        return len(self.y_train)

train_dataset = MyDataset(x_train, y_train)

''' 
数据和标签组成数据集
'''

train_loader = Data.DataLoader(train_dataset, batch_size=16, shuffle=True)

'''
加载数据集
数据集
批大小
是否打乱顺序
'''
# iter(train_loader).next()
# print(iter(train_loader).next())
'''
def main():
    number = 23

    coder = fizzbuzz_encoder(number)

    classification = fizzbuzz_decoder(number, coder)

    print("数字 %d 的类别为:%s \n" %(number, classification)) 
'''
class MyModel(nn.Module):
    def __init__(self):
        super(MyModel, self).__init__()
        self.linear1 = nn.Linear(10, 64) # 线性层
        self.activation = nn.ReLU()
        self.linear2 = nn.Linear(64, 8)
        self.linear3 = nn.Linear(8, 4)

    def forward(self, x):
        
        output = self.linear1(x)  # [batch_size, 64]
        output = self.activation(output)  # [batch_size, 64]
        output = self.linear2(output)  # [batch_size, 8]
        output = self.linear3(output)  # [batch_size, 4]
        return output

# model = MyModel().to(device)
model = MyModel()

loss_fn = nn.CrossEntropyLoss()

optimizer = optim.Adam(model.parameters(), lr=1e-2)

Epoch = 100

for epoch in range(Epoch):
    for x, y in train_loader:
        # x, y = x.to(device), y.to(device)
        pred = model(x)
        loss = loss_fn(pred, y)
        print(loss)

        loss.backward()
        optimizer.step()
        optimizer.zero_grad()

torch.save(model.state_dict(), 'testmodel1')


number = 31

x_test = torch.Tensor([binary_encoder(number)])

pred = model(x_test)
 
softmax = nn.Softmax()

pred = softmax(pred)

classification = np.argmax(pred.detach().numpy(), 1)

print("数字 %d 的类别为:%s \n" %(number, classification))



# print(x_train[0:5,])
# print(y_train)
# print(x_train[:5])
# print(x_train[0:5,:])

'''
if __name__ == '__main__':
    for i in range(1,16):
        test(i)
'''

'''
number = 1500

x_test = torch.Tensor([binary_encoder(number)])

model.load_state_dict(torch.load('testmodel1'))

pred = model(x_test)
 
softmax = nn.Softmax()

pred = softmax(pred)

classification = np.argmax(pred.detach().numpy(), 1)

print("数字 %d 的类别为:%s \n" %(number, classification))
'''


GPU

import torch
import numpy
import torch.nn as nn
import torch.optim as optim
import torch.nn.functional as F
import torch.utils.data as Data
from PIL import Image
import numpy as np

device = torch.device('cuda' if torch.cuda.is_available() else 'cpu')


def number_determinate(number):
    '''
    只是实现了这么一个功能,却没理解这样做的含义
    '''
    if number % 15 == 0:
        return 3
    elif number % 5 == 0:
        return 2
    elif number % 3 == 0:
        return 1
    return 0


def fizzbuzz_encoder(number):
    '''
    把抽象的表述变为数字的过程成为编码
    '''
    # 'fizzbuzz'
    if number % 15 == 0:
        return 3
    # 'buzz'
    elif number % 5 == 0:
        return 2
    # 'fizz'
    elif number % 3 == 0:
        return 1
    # str(number)
    return 0

def fizzbuzz_decoder(number, lebal):
    '''
    将计算机内部自定义的编码信息转成自然语言表示
    '''
    return [str(number), 'fizz', 'buzz', 'fizzbuzz'][lebal]

def test(number):
    print("数字 %d 的类别为:%s \n" %(number, fizzbuzz_decoder(number, fizzbuzz_encoder(number))))

def binary_encoder(number):
    '''
    number相当于数据集本身特征,这里将number编码为二进制形式,以表示更多特征
    '''
    NUM_DIGITS = 10
    return np.array([number >> d & 1 for d in range (NUM_DIGITS)][::-1])

x_train = torch.Tensor([binary_encoder(number) for number in range(101, 1024)])
y_train = torch.LongTensor([fizzbuzz_encoder(number) for number in range(101, 1024)])


class MyDataset(Data.Dataset):
    '''
    先定义(继承)类(函数重写)
    '''
    def __init__(self, x_train, y_train):
        self.x_train = x_train
        self.y_train = y_train
    def __getitem__(self, index):
        return self.x_train[index], self.y_train[index]
    def __len__(self):
        return len(self.y_train)

train_dataset = MyDataset(x_train, y_train)

''' 
数据和标签组成数据集
'''

train_loader = Data.DataLoader(train_dataset, batch_size=16, shuffle=True)

'''
加载数据集
数据集
批大小
是否打乱顺序
'''
# iter(train_loader).next()
# print(iter(train_loader).next())
'''
def main():
    number = 23

    coder = fizzbuzz_encoder(number)

    classification = fizzbuzz_decoder(number, coder)

    print("数字 %d 的类别为:%s \n" %(number, classification)) 
'''
class MyModel(nn.Module):
    def __init__(self):
        super(MyModel, self).__init__()
        self.linear1 = nn.Linear(10, 64) # 线性层
        self.activation = nn.ReLU()
        self.linear2 = nn.Linear(64, 8)
        self.linear3 = nn.Linear(8, 4)

    def forward(self, x):
        
        output = self.linear1(x)  # [batch_size, 64]
        output = self.activation(output)  # [batch_size, 64]
        output = self.linear2(output)  # [batch_size, 8]
        output = self.linear3(output)  # [batch_size, 4]
        return output

model = MyModel().to(device)

loss_fn = nn.CrossEntropyLoss()

optimizer = optim.Adam(model.parameters(), lr=1e-2)

Epoch = 10

for epoch in range(Epoch):
    for x, y in train_loader:
        x, y = x.to(device), y.to(device)
        pred = model(x)
        loss = loss_fn(pred, y)
        print(loss)

        loss.backward()
        optimizer.step()
        optimizer.zero_grad()

# print(x_train[0:5,])
# print(y_train)
# print(x_train[:5])
# print(x_train[0:5,:])

'''
if __name__ == '__main__':
    for i in range(1,16):
        test(i)
'''

测试

import torch
import numpy
import torch.nn as nn
import torch.optim as optim
import torch.nn.functional as F
import torch.utils.data as Data
from PIL import Image
import numpy as np


def binary_encoder(number):
    '''
    number相当于数据集本身特征,这里将number编码为二进制形式,以表示更多特征
    '''
    NUM_DIGITS = 10
    return np.array([number >> d & 1 for d in range (NUM_DIGITS)][::-1])


class MyModel(nn.Module):
    def __init__(self):
        super(MyModel, self).__init__()
        self.linear1 = nn.Linear(10, 64) # 线性层
        self.activation = nn.ReLU()
        self.linear2 = nn.Linear(64, 8)
        self.linear3 = nn.Linear(8, 4)

    def forward(self, x):
        
        output = self.linear1(x)  # [batch_size, 64]
        output = self.activation(output)  # [batch_size, 64]
        output = self.linear2(output)  # [batch_size, 8]
        output = self.linear3(output)  # [batch_size, 4]
        return output


model = MyModel()    


number = 300

x_test = torch.Tensor([binary_encoder(number)])

model.load_state_dict(torch.load('testmodel1'))

pred = model(x_test)
 
softmax = nn.Softmax()

pred = softmax(pred)

classification = np.argmax(pred.detach().numpy(), 1)

print("数字 %d 的类别为:%s \n" %(number, classification))
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值