cifar-10简介
cifar-10是一个有十个类的32*32色图片数据集,共有60000张。官方网址如下:
http://www.cs.toronto.edu/~kriz/cifar.html
我在官方网站上下载了这个数据集的python版。
官网上对该数据集作了一些描述
1.该数据集的data是10000X3072的numpy数组。每张32*32=1024的图用3072个数表示其各像素点的RGB值,前1024表示红色值,接下来1024表示绿色值,最后1024表示蓝色值。
2.该数据集的label值表示这些图的标签,用0-9表示。
3.label_names表示各个label数表示的标签类别的英文名。
4.data_batch_1到data_batch_5以及test_batch这几个文件每个文件都存了10000张图片以及其描述,其中test_batch是用来做测试的。
准备工作
官网上比较关键的信息就这些了,具体的内容还是手动操作一下吧。
打开pycharm新建一个项目,结构如下:
然后依次给项目对应的虚拟环境装上numpy,matplotlib,pandas,tensorflow
这个东西直接在pycharm环境里面配置好就行了,应该不会遇到什么问题。
首先我们写个程序来看看这些数据集里都是什么玩意儿
import pickle
import matplotlib.pyplot as plt
import numpy as np
import os
import tensorflow as tf
# 数据集的根目录
CIFAR_10_PATH = "./cifar-10-batches-py"
# 打开这个根目录下的data_batch_1文件看看
with open(os.path.join(CIFAR_10_PATH, "data_batch_1"), "rb") as f:
# python3需要额外指出编码类型为二进制
data = pickle.load(f, encoding="bytes")
# 看一下这个文件的数据类型,可以看到是字典型的
print("1.data的类型:")
print(type(data))
# data应该就是前面说的图片数据了
print("2.data的keys:")
print(data.keys())
# 因为数据时二进制存储的python3这前面得加个b,可以看到,这玩意是个numpy数组
print("3.data[b'data']的类型:")
print(type(data[b'data']))
# filenames
print("4.data[b'filenames']的类型:")
print(type(data[b'filenames']))
# batch_label
print("5.data[b'batch_label']的类型:")
print(type(data[b'batch_label']))
# labels
print("6.data[b'labels']的类型:")
print(type(data[b'labels']))
# 和文章描述的一样,是10000*3072的
print("7.data[b'data']的shape:")
print(data[b'data'].shape)
# 这个labels是一个10000的数组,看起来是各个图片的标签
print("8.data[b'labels']的长度:")
print(len(data[b'labels']))
# 这个是各个图片的文件名
print("9.data[b'filenames']的前两个内容:")
print(data[b'filenames'][0:2])
# 这玩意是文件名
print("10.data[b'batch_label']的内容:")
print(data[b'batch_label'])
输出结果:
1.data的类型:
<class 'dict'>
2.data的keys:
dict_keys([b'filenames', b'data', b'labels', b'batch_label'])
3.data[b'data']的类型:
<class 'numpy.ndarray'>
4.data[b'filenames']的类型:
<class 'list'>
5.data[b'batch_label']的类型:
<class 'bytes'>
6.data[b'labels']的类型:
<class 'list'>
7.data[b'data']的shape:
(10000, 3072)
8.data[b'labels']的长度:
10000
9.data[b'filenames']的前两个内容:
[b'leptodactylus_pentadactylus_s_000004.png', b'camion_s_000148.png']
8.data[b'batch_label']的长度:
b'training batch 1 of 5'
这样一来,结合着官网上的描述,我们就基本搞清楚这些文件的结构了
用matplotlib.pyplot显示一张图片看看效果
这里的话会涉及到numpy的一些东西
代码如下
import pickle
import matplotlib.pyplot as plt
import numpy as np
import os
import tensorflow as tf
# 数据集的根目录
CIFAR_10_PATH = "./cifar-10-batches-py"
# 打开这个根目录下的data_batch_1文件看看
with open(os.path.join(CIFAR_10_PATH, "data_batch_1"), "rb") as f:
# python3需要额外指出编码类型为二进制
data = pickle.load(f, encoding="bytes")
# 看一下这个文件的数据类型,可以看到是字典型的
print("data的keys:")
print(data.keys())
# 取第一张图片的数据
t = data[b'data'][0]
# 按照文档里说的,图片是以1024+1024+1024的方式线性存储各像素点的色值得,我们得把他处理成能显示的类型。我们先把原数组划分为一个3*32*32的np对象
t = t.reshape(3, 32, 32)
# transpose方法中,如一个点坐标为(1,2,3)对其作(1,2,0)的变换,则其新坐标为(2,3,1),即原本的0轴坐标变为1轴坐标,1轴坐标变为2轴坐标,2轴坐标变为0轴。同时,整个numpy对象的shape也会发生这样的变换
# t.transpose(1, 2, 0)可以将原本格式的数据转换成32*32*3的形式,且这个3是二维图片的每个像素点的RGB三元组的值。
# 变换后,原本的第一个(0,0,0)位置上的数成了二维平面上第一个像素位置上(0,0)的第一个红色值,(2,0,0)成了(0,0)上的绿色值,以此类推
t = t.transpose(1, 2, 0)
# 使用plt中的方法将这张图片显示出来看看
plt.imshow(t)
plt.show()
效果如下,图片原本是32*32的,放大了以后就变得这么丑了,说实话我也没看出来这玩意是什么。。。应该是青蛙或则狗吧—.—
简单二分类器的实现
这里取cifar10数据集中标签为0和1的数据,使用一个神经元,用逻辑斯蒂二分类模型实现了对图像的分类,用p_y_1=sigmoid(_y)表示预测标签为1的概率,若p_y_1>0.5,则预测标签为1,否则,预测标签为0。模型很简单,比较麻烦的地方还是在数据的处理上。
import pickle
import numpy
import os
import matplotlib.pyplot
CIFAR_PATH = './cifar10'
'''load data from package'''
def load_data(filename):
with open(os.path.join(CIFAR_PATH,filename),'rb') as f:
data = pickle.load(f,encoding = 'bytes')
return data[b'data'],data[b'labels']
# 对数据集进行管理
class CifarData:
def __init__(self, filenames, need_shuffle):
all_datas = []
all_labels = []
for filename in filenames:
datas,labels = load_data(filename)
for data,label in zip(datas,labels) :
if label in [0, 1]:
all_datas.append(data)
all_labels