您的位置:首页 > 编程语言 > Python开发

机器学习(10.1)--手写数字识别的不同算法比较(1)--mnist数据集不同版本解析及平均灰度实践

2018-02-23 15:20 531 查看
现在网上流行的mnist数据集共有两个版本
1、tensorflow 提供的 点击此处下载
2、开源标准数据集    点击此处下载

连续向下的几篇文章将是一套系列文章,都是对mnist的开源
标准数据集进行手写数字识别的
在我之前的所有文章多是在tensorflow内容才使用到mnist,因此,基本使用的是tensorflow 提供的版本
在这个系列的文章,我不依赖tensorflow,应用基本机器学习方法来进行手写数字识别,因此更多的会应用开源标准数据集的这个版本

这两个版本内部基本是一致,只是初始调用时的格式与数据量略有不同,都是由训练、交叉验证、测试三个集合组成,
仔细看看后面代码,就可以明白不同的调用方式,挺简单的,反正就是调用,没什么可多说的

后面附带了一段平均灰度(Average Darkness)算法,
这个算法比较简单,只是顺手写写,算是知道有这个算法而已,
因为至少运用mnist手写识别率上实在低的可怜只有22.25%# -*- coding:utf-8 -*-

from tensorflow.examples.tutorials.mnist import input_data
mnist_tensorflow=input_data.read_data_sets("MNIST_data/", one_hot=True)
print("tensorflow提供的mnist:")
print("数据的初始类型为:"+str(type(mnist_tensorflow)))
print("训练集共有图像:%d条,训练结果:%d条"%(len(mnist_tensorflow.train.images),len(mnist_tensorflow.train.labels)))
print("交叉验证集共有图像:%d条,训练结果:%d条"%(len(mnist_tensorflow.validation.images),len(mnist_tensorflow.validation.labels)))
print("测试集共有图像:%d条,训练结果:%d条"%(len(mnist_tensorflow.test.images),len(mnist_tensorflow.test.labels)))
print("图像集的类型为:"+str(type(mnist_tensorflow.train.images)))
print("结果集的类型为:"+str(type(mnist_tensorflow.train.labels)))
print("单张图片的数据维度为:"+str(mnist_tensorflow.train.images[0].shape))
print("单张结果的数据维度为:"+str(mnist_tensorflow.train.labels[0].shape))#(10,)
print("单张结果的数据为:"+str(mnist_tensorflow.train.labels[0])) #[0. 0. 0. 0. 0. 0. 0. 1. 0. 0.]
print("单张结果的数据单个元素类型为:"+str(type(mnist_tensorflow.train.labels[0][0])))

print('-'*60)
import pickle
import gzip
with gzip.open(r'mnist.pkl.gz', 'rb') as f:
training_data, validation_data, test_data = pickle.load(f,encoding='bytes')
print("开源标准数据集的信息如下:")
print("训练集初始类型为元组:"+str(type(training_data))+";共"+str(len(training_data))+"个元素,第一个元素为图片集,第二个元素为结果集")
print("训练集共有图像:%d条,训练结果:%d条"%(len(training_data[0]),len(training_data[1])))
print("交叉验证共有图像:%d条,训练结果:%d条"%(len(validation_data[0]),len(validation_data[1])))
print("测试集共有图像:%d条,训练结果:%d条"%(len(test_data[0]),len(test_data[1])))
print("图像集的类型为:"+str(type(training_data[0])))
print("结果集的类型为:"+str(type(training_data[1])))
print("单张图片的数据维度为:"+str(training_data[0][0].shape))
print("单张结果的数据维度为:"+str(training_data[1][0].shape)) #()
print("单张结果的数据为:"+str(training_data[1][0])) #5

print('-'*60)

print(
'''
两个集的的最大差异在于单张图片所以应的结果上
1、tensorflow 的结果一个是10 个元素的数组,[0. 0. 0. 0. 0. 0. 0. 1. 0. 0.]
在这10元素,只有1个是1,剩余9个是0,当1在第几位则表示这是数据几,如上面这个表示为7
请注意,这里的每个元素不是int型,是numpy.float64
2、而在开源标准数据集是数字几就表示几
这两种方式的转化很容易
''')
print('-'*60)
print("以下为相互转化的简单方法")
import numpy as np
#由tensorflow的结果转为数字
value_tensorflow=[0., 0., 0., 0., 0., 0., 0. ,1., 0., 0.]
value_tensorflow_toOpensource=np.argmax(value_tensorflow)
print(value_tensorflow_toOpensource)

#由数字转为tensorflow的结果
value_opensource=5
value_opensource_toTensorflow=np.zeros(10)
value_opensource_toTensorflow[value_opensource]=1
print(value_opensource_toTensorflow)


平均灰度(Average Darkness)算法,
# -*- coding:utf-8 -*-
import pickle
import gzip
import numpy as np
with gzip.open(r'mnist.pkl.gz', 'rb') as f:
training_data, validation_data, test_data = pickle.load(f,encoding='bytes')
#计算测试集与训练集每张图片的数据的和
training_data= list(zip(np.sum(training_data[0],axis=1),training_data[1]))
test_data= list(zip(np.sum(test_data[0],axis=1),test_data[1]))

#计算训练集的每个数字的平均灰度
avgs=np.zeros(10)
for i in range(10):
numer_data=list(filter(lambda x: x[1]==i,training_data))
avgs[i]=np.mean(numer_data,axis=0)[0]
print(avgs)

count=0
for i in test_data:
if np.argmin(abs(avgs-i[0]))==i[1]: count+=1
print("计算完成,正确条数为:%d"%count+",正确率为"+str(round(count/len(test_data)*100,2))+"%")
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
相关文章推荐