[keras]用CNN来刷Kaggle的digit手写数据集比赛

keras实战

keras是比较适合新手的深度框架,不说废话,一切代码全是手敲,有问题可以留言共同交流。

1.处理数据

从kaggle官方下载数据集,地址:https://www.kaggle.com/c/digit-recognizer/data
拿到手之后是主要是train.csv 和 test.csv ,提交结果类型是out.csv

import keras
from keras.models import Sequential
from keras.layers import Dense,Dropout,Flatten,MaxPool2D,Conv2D
import pandas as pd
import numpy as np
from keras import backend as K

首先import 需要的包

BATCH_SIZE = 128   #每次训练或者test时的大小
NUM_CLASSES = 10   # 结果分成十类 从 0-9
EPOCHS = 12        # 我们训练12轮
img_rows ,img_cols = 28,28  图片原始大小时 28 * 28 其实我们拿到的时已经拉平的数据

定义一些常量

train_data = pd.read_csv('train.csv')  # 读取train数据
test_data = pd.read_csv('test.csv')    # 读取test 数据
train_x ,train_y = train_data.values[:,1:] , train_data.values[:,0] # 分割数据把label拿出来
test_x = test_data.values # 
## 将 train_y 进行都热向量编码  ont_hot编码 其实就是把结果搞成稀疏矩阵
train_y = keras.utils.np_utils.to_categorical(train_y,num_classes=NUM_CLASSES)
print(train_y)

将数据进行一些shape变换,因为一会要用来做卷积

train_x = np.reshape(train_x,[-1, 28, 28, 1])
print(np.shape(train_x))
test_x = np.reshape(test_x,[-1, 28, 28, 1])
print(np.shape(test_x))

这个时候我们打印一下 keras的图片格式

print(K.image_data_format())

数据归一化

train_x = train_x.astype('float32') / 255
test_x = test_x.astype('float32') / 255
input_shape = (img_rows, img_cols, 1)

构造网络模型 我们采用序贯模型

model = keras.models.Sequential()

增加 通道为32 的 卷积核大小为3 的卷积 激活函数为relu 输入图片的大小为 28 * 28 * 1

model.add(Conv2D(32,(3,3),
                 activation='relu',
                 input_shape=(28,28,1)
                ))

再来一层

model.add(Conv2D(64,(3,3),
                 activation='relu',
                 input_shape=(28,28,1)
                ))

加一个 池化层 和dropout层


model.add(MaxPool2D(pool_size=(2,2)))
model.add(Dropout(0.5))
## 增加flattern层 把结果拉成一个列向量
model.add(Flatten())
## 加一个全连接层
model.add(Dense(128,activation='relu'))
model.add(Dropout(0.5))
## 再加一个全链接层  softmax来预测全概率
model.add(Dense(NUM_CLASSES,activation='softmax'))
#编译模型
model.compile(loss=keras.metrics.categorical_crossentropy,optimizer=keras.optimizers.Adam(),metrics=['accuracy'])


model.fit(train_x, train_y, batch_size=BATCH_SIZE, epochs=EPOCHS,
          verbose=1)

CLASSES = model.predict_classes(test_x,batch_size=BATCH_SIZE)
#print(CLASSES)
#输出结果 在kaggle上可以直接提交
pd.DataFrame(
    {"ImageId": range(1, len(CLASSES) + 1), "Label": CLASSES}
).to_csv('output.csv', index=False, header=True)
print('done.')

[keras]用CNN来刷Kaggle的digit手写数据集比赛_第1张图片

完整代码在这里:


# coding: utf-8
## kears mnist
import keras
from keras.models import Sequential
from keras.layers import Dense,Dropout,Flatten,MaxPool2D,Conv2D
import pandas as pd
import numpy as np
from keras import backend as K


BATCH_SIZE = 128
NUM_CLASSES = 10
EPOCHS = 12
img_rows ,img_cols = 28,28


train_data = pd.read_csv('train.csv')
test_data = pd.read_csv('test.csv')
train_x ,train_y = train_data.values[:,1:] , train_data.values[:,0]
test_x = test_data.values
## 将 train_y 和test_y 进行都热向量编码
train_y = keras.utils.np_utils.to_categorical(train_y,num_classes=NUM_CLASSES)
## 将 traion_x 和 test_x 进行reshape


train_x = np.reshape(train_x,[-1, 28, 28, 1])
print(np.shape(train_x))
test_x = np.reshape(test_x,[-1, 28, 28, 1])
print(np.shape(test_x))

print(K.image_data_format())


## 归一化
train_x = train_x.astype('float32') / 255
test_x = test_x.astype('float32') / 255
input_shape = (img_rows, img_cols, 1)

## 构造网络模型
model = keras.models.Sequential()


# 增加 通道为32 的 卷积核大小为3 的卷积  激活函数为relu  输入图片的大小为 28 * 28 * 1
model.add(Conv2D(32,(3,3),
                 activation='relu',
                 input_shape=(28,28,1)
                ))


model.add(Conv2D(64,(3,3),
                 activation='relu',
                 input_shape=(28,28,1)
                ))
## 池化层
model.add(MaxPool2D(pool_size=(2,2)))
# 增加dropout层
model.add(Dropout(0.5))

## 增加flattern层 把结果拉成一个列向量
model.add(Flatten())
## 加一个全连接层
model.add(Dense(128,activation='relu'))
model.add(Dropout(0.5))
## 再加一个全链接层  softmax来预测全概率
model.add(Dense(NUM_CLASSES,activation='softmax'))

## 编译模型
model.compile(loss=keras.metrics.categorical_crossentropy,optimizer=keras.optimizers.Adam(),metrics=['accuracy'])


model.fit(train_x, train_y, batch_size=BATCH_SIZE, epochs=EPOCHS,
          verbose=1)

CLASSES = model.predict_classes(test_x,batch_size=BATCH_SIZE)
pd.DataFrame(
    {"ImageId": range(1, len(CLASSES) + 1), "Label": CLASSES}
).to_csv('output.csv', index=False, header=True)
print('done.')

模型可视化 //TODO 这一点还没找到可靠的解决方案

我们希望能够看到自己构建的model到底长什么样子,keras提供了可视化的方法:
注意这个错误:

Failed to import pydot. You must install pydot and graphviz for `pydotprint` to work.

解决方案:http://blog.csdn.net/hahajinbu/article/details/72859849

from keras.utils import plot_model
plot_model(model, to_file='model.png')

思考TODO

1.如何进一步的提高准确率,在之前用PCA和SVM配合使用的情况效果也不错,是否可以用PCA先进行一下数据特征抽取和降低维度,是否对CNN有所帮助
2.训练数据时耗时并且麻烦的,是否可以直接用迁移学习的迁移模型比如VGG等
3….
代码是比较简单的,但是背后的知识点还是很多的

你可能感兴趣的:(cnn卷积神经网络,keras)