Tensorflow:批处理整个数据集(MNIST 教程)

Tensorflow: Batching whole dataset (MNIST Tutorial)

学习本教程:https://www.tensorflow.org/versions/r1.3/get_started/mnist/pros

我想自己解决一个带标签图像的分类问题。由于我没有使用 MNIST 数据库,我花了几天时间在 tensorflow 中创建自己的数据集。它看起来像这样:

#variables
batch_size = 50
dimension = 784
stages = 10

#step 1 read Dataset
filenames = tf.constant(filenamesList)
labels = tf.constant(labelsList)

#step 2 create Dataset
dataset = tf.data.Dataset.from_tensor_slices((filenames, labels))

#step 3: parse every image in the dataset using `map`
def _parse_function(filename, label):
    #convert label to one-hot encoding
    one_hot = tf.one_hot(label, stages)

    #read image file
    image_string = tf.read_file(filename)
    image_decoded = tf.image.decode_image(image_string, channels=3)
    image = tf.cast(image_decoded, tf.float32)

    return image, one_hot

#step 4 final input tensor
dataset = dataset.map(_parse_function)
dataset = dataset.batch(batch_size) #batch_size = 100

iterator = dataset.make_one_shot_iterator()
images, labels = iterator.get_next()

images = tf.reshape(images, [batch_size,dimension]).eval()
labels = tf.reshape(labels, [batch_size,stages]).eval()

for _ in range(10):
    dataset = dataset.shuffle(buffer_size = 100)
    dataset = dataset.batch(batch_size)
    iterator = dataset.make_one_shot_iterator()
    images, labels = iterator.get_next()

    images = tf.reshape(images, [batch_size,dimension]).eval()
    labels = tf.reshape(labels, [batch_size,stages]).eval()

    train_step.run(feed_dict={x: images, y_:labels})

不知何故,使用 更高的 batch_sizes 会破坏 python。我想要做的是在每次迭代时用新的批次训练我的神经网络。这就是为什么我也使用 dataset.shuffle(...)。使用 dataset.shuffle 也会破坏我的 Python.

我想做的(因为洗牌中断)是对整个数据集进行批处理。通过评估 ('.eval()') 我将得到一个 numpy 数组。然后我将使用 numpy.random.shuffle(images) 对数组进行洗牌,然后选择一些第一个元素来训练它。

例如

for _ in range(1000):
    images = tf.reshape(images, [batch_size,dimension]).eval()
    labels = tf.reshape(labels, [batch_size,stages]).eval()

    #shuffle
    np.random.shuffle(images)
    np.random.shuffle(labels)

    train_step.run(feed_dict={x: images[0:train_size], y_:labels[0:train_size]})

但随之而来的问题是我无法对整个数据集进行批处理。看起来数据太大 python 无法使用。 我应该如何以不同的方式解决这个问题?

因为我没有使用 MNIST 数据库,所以没有像 mnist.train.next_batch(100) 这样的功能对我来说很方便。

请注意您如何在 循环中调用 shufflebatch ?这是错误的。 TF 中的 Datasets 以函数式编程的方式工作,因此您实际上是在定义一个管道来预处理数据以输入到您的模型中。在某种程度上,你给出了一个回答问题的食谱 "given this raw data, which operations (map, etc.) should I do to get batches that I can feed into my neural network?"

现在您正在为每个批次修改该管道!发生的是第一次迭代,批量大小是 [32 3600]。下一次迭代,这个形状的元素再次被批处理,到[32 32 3600],依此类推。

有一个很棒的 tutorial on the TF website,您可以在其中找到更多 Dataset 的工作原理,但这里有一些解决问题的建议。

  • 在您的代码中将洗牌移动到 "Step 2" 之后。然后你正在洗牌整个数据集,这样你的批次就会有很好的例子混合。同时增加 buffer_size 参数,这在 中有效。尽早打乱通常是个好主意,因为如果你有一个大数据集,这可能是一个缓慢的操作——数据集的打乱部分必须读入内存。在这里,您是打乱文件名和标签,还是读取图像和标签并不重要——但后者将有更多工作要做,因为那时数据集更大。

  • 将批处理和迭代器生成器移到最后一步,就在开始训练循环之前。

  • 不要使用 feed_dictDataset 迭代器将数据输入到模型中。相反,根据 iterator.get_next() 的输出定义您的模型并省略 feed_dict 参数。从这个问答中查看更多详细信息:

我在创建 tensorflow 数据集时遇到了很多问题。所以我决定用OpenCV导入图片

import opencv as cv
imgDataset = []
for i in range(len(files)):
    imgDataset.append(cv2.imread(files[i]))
imgDataset = np.asarray(imgDataset)

imgDataset 的形状为(num_img,高度,宽度,col_channels)。获取 i-th 图像应该是 imgDataset[i].

可以像这样打乱数据集并只获取其批次:

from sklearn.utils import shuffle
X,y = shuffle(X, y)
X_feed = X[batch_size]
y_feed = y[batch_size]

然后将 X_feed 和 y_feed 馈入模型