FizzBuzz是一个简单的小游戏,游戏规则如下:
1)从1开始往上数数,当遇到3的倍数的时候,说fizz;
2)当遇到5的倍数,说buzz;
3)当遇到15的倍数,就说fizzbuzz;
4)其他情况下则正常数数。
现在要求使用神经网络实现FizzBuzz问题。
FizzBuzz问题本质上是一个四分类问题,即输入一个数字,我们需要将其分为数字本身、Fizz、Buzz、FizzBuzz其中的一类。我们可以搭建一个神经网络,其输入层、隐层、输出层均为全连接层,借助它完成分类任务,进而解决问题。
代码示例
1、定义转码解码函数
# 可以理解为转化为type def fb_encode(i): if i % 15 == 0: return 0 elif i % 5 == 0: return 1 elif i % 3 == 0: return 2 else: return 3 # 根据类型值转化 def fb_decode(i, type): return ['fizzbuzz', 'buzz', 'fizz', str(i)][type] # # 测试 # for i in range(1, 101): # print(fb_decode(i, fb_encode(i)))
2、定义训练集
有了前面的转码解码函数,现在问题就转化成了4分类问题,只需要通过深度学习,找到数值和type的对应关系即可。
# 整数值转化为10位二进制列表 def to_binary(i): bstr = str(bin(i))[2:].zfill(10) return list(map(int, bstr)) import torch # 1-100做测试数据,从101开始 x_train = torch.FloatTensor([to_binary(i) for i in range(101, pow(2, 10))]) y_train = torch.LongTensor([fb_encode(i) for i in range(101, pow(2, 10))]) # 分类问题,注意long类型
3、定义模型
import torch.nn as nn D_h = 100 model = nn.Sequential( nn.Linear(10, D_h), nn.ReLU(D_h), nn.Linear(D_h, 4) ) loss_fn = nn.CrossEntropyLoss() optimizer = torch.optim.Adam(model.parameters(), lr=0.001)
4、模型训练
for it in range(3000): for batch_start in range(0, len(x_train), 64): batch_end = batch_start + 64 x = x_train[batch_start:batch_end] y = y_train[batch_start:batch_end] y_hat = model(x) loss = loss_fn(y_hat, y) print(it, loss.item()) optimizer.zero_grad() loss.backward() optimizer.step()
5、基于模型做预测
import numpy as np x_test = torch.FloatTensor([to_binary(i) for i in range(1, 101)]) y_pred = model(x_test).max(1)[1].tolist() # 展示真实值和预测值 for i,type in zip(range(1,101), y_pred): print(i, fb_decode(i, fb_encode(i)), fb_decode(i, type)) # 计算准确率 np_true = np.array([fb_encode(i) for i in range(1,101)]) np_pred = np.array(y_pred) print('ACC:', (np_true == np_pred).sum()/len(np_true))
本文为 陈华 原创,欢迎转载,但请注明出处:http://ichenhua.cn/read/313