import numpy as np
import matplotlib.pyplot as plt
import torch
import copy
import torch.nn as nn
from torchvision.datasets import FashionMNIST
from torchvision import transforms
import torch.utils.data as Data
import csv
import gzip
import pandas as pd
import os
from torch.autograd import Variable
读取数据集
class DealDataset(Data.Dataset):
"""
读取数据、初始化数据
"""
def __init__(self, folder, data_name, label_name, transform=None):
(train_set, train_labels) = load_data(folder, data_name,label_name)
# 其实也可以直接使用torch.load(),读取之后的结果为torch.Tensor形式
self.train_set = train_set
self.train_labels = train_labels
self.transform = transform
def __getitem__(self, index):
img, target = self.train_set[index], int(self.train_labels[index])
if self.transform is not None:
img = self.transform(img)
return img, target
def __len__(self):
return len(self.train_set)
def load_data(data_folder, data_name, label_name):
with open(os.path.join(data_folder, label_name), 'rb') as lbpath: # rb表示的是读取二进制数据
y_train = np.frombuffer(lbpath.read(), np.uint8, offset=8)
with open(os.path.join(data_folder, data_name), 'rb') as imgpath:
x_train = np.frombuffer(
imgpath.read(), np.uint8, offset=16).reshape(len(y_train), 28, 28)
return (x_train, y_train)
train_set = DealDataset('datasets/zalando-research-fashionmnist-momodel',
"train-images-idx3-ubyte",
"train-labels-idx1-ubyte",
transform=transforms.ToTensor())
# 训练数据和测试数据的装载
train_loader = torch.utils.data.DataLoader(
dataset=train_set,
batch_size=64, # 一个批次可以认为是一个包,每个包中含有10张图片
shuffle=True,
)
test_set = DealDataset('datasets/zalando-research-fashionmnist-momodel',
"t10k-images-idx3-ubyte",
"t10k-labels-idx1-ubyte",
transform=transforms.ToTensor())
test_loader = torch.utils.data.DataLoader(
dataset=test_set,
batch_size=1000, # 一个批次可以认为是一个包,每个包中含有10张图片
shuffle=False,
)
test_x,test_y=next(iter(test_loader))
test_x = Variable(test_x[:1000]).type(torch.FloatTensor)/255.
test_y=test_y[:1000]
print(test_x.shape,test_y.shape)
网络
class MyNet(nn.Module):
def __init__(self):
super(MyNet,self).__init__()
self.conv1=nn.Sequential(
nn.Conv2d(1,16,3,1,1),
nn.ReLU(),
nn.AvgPool2d(2,2))
self.conv2=nn.Sequential(
nn.Conv2d(16,32,3,1,0),
nn.ReLU(),
nn.AvgPool2d(2,2))
self.classifier=nn.Sequential(
nn.Linear(32*6*6,256),
nn.ReLU(),
nn.Linear(256,128),
nn.ReLU(),
nn.Linear(128,10))
def forward(self,x):
x=self.conv1(x)
x=self.conv2(x)
x=x.view(x.size(0),-1)
out=self.classifier(x)
return out
def train(model,train_data,criterion,optimizer,num_iters=10):
train_loss_all=[]
train_acc_all=[]
# best_w=copy.deepcopy(model.state_dict())
model.train()
for epoch in range(num_iters):
train_loss,train_acc=0.0,0
train_num=0
for step,(x,y) in enumerate(train_data):
out=model(x)
pre_lab=torch.argmax(out,1)
loss=criterion(out,y)
optimizer.zero_grad()
loss.backward()
optimizer.step()
train_num+=y.size(0)
train_loss+=loss.item()*x.size(0)
train_acc+=torch.sum(pre_lab==y.data)
train_loss_all.append(train_loss/train_num)
train_acc_all.append(train_acc.double().item()/train_num)
print("Epoch{}/{},train_loss:{},train_acc:{}".format(epoch+1,num_iters,
train_loss_all[-1],train_acc_all[-1]))
训练
net=MyNet()
# print(net)
optimizer=torch.optim.Adam(net.parameters(),lr=0.001)
criterion=nn.CrossEntropyLoss()
train(net,train_loader,criterion,optimizer,num_iters=10)
Epoch1/10,train_loss:0.5776334433873495,train_acc:0.7821666666666667 Epoch2/10,train_loss:0.3761489192008972,train_acc:0.86045 Epoch3/10,train_loss:0.31849680088361104,train_acc:0.8819333333333333 Epoch4/10,train_loss:0.2837980465332667,train_acc:0.8954 Epoch5/10,train_loss:0.2579363843202591,train_acc:0.90455 Epoch6/10,train_loss:0.23616223863561947,train_acc:0.91195 Epoch7/10,train_loss:0.21970758376518884,train_acc:0.9182333333333333 Epoch8/10,train_loss:0.20625990916887918,train_acc:0.9232666666666667 Epoch9/10,train_loss:0.19077128770748775,train_acc:0.92915 Epoch10/10,train_loss:0.17777039955457052,train_acc:0.9341166666666667