我不明白图像实际上是如何输入 CNN 的。如果我有一个包含几千张图像的目录,我需要采取哪些步骤才能将它们提供给神经网络(例如调整大小、灰度、标记等)?我不明白图像的标签是如何工作的。这个数据集实际上会是什么样子?或者你可以不看它(像一张桌子)?
如何为 CNN 构建图像数据集?
这是一个非常紧凑的问题。让我们尝试通过它,我将尝试提供一些使用 CNN 进行图像处理的示例。
预处理数据
预处理数据(例如调整大小和灰度)是机器学习管道的第一步。大多数深度学习框架都要求您的训练数据具有相同的形状。因此,最好将图像大小调整到某个标准。
每当训练任何类型的机器学习模型时,记住偏差方差权衡是很重要的。模型越复杂,训练就越困难。这意味着最好限制模型中模型参数的数量。您可以通过对图像进行下采样来减少模型的输入数量。出于同样的原因,通常使用灰度。如果图像中的颜色不包含任何区别信息,那么您可以通过灰度化将输入数量减少三分之一。
根据您的数据,可以使用许多其他预处理方法。做一些数据增强也是一个好主意,这是在不改变结果标签的情况下稍微改变你的输入数据,以增加你必须训练模型的实例数量。
如何组织数据?
您将用作 CNN 输入的变量的形状取决于您选择的包。我更喜欢使用谷歌开发的tensorflow。如果您打算使用非常标准的架构,那么有一个非常有用的包装库,名为 Keras,它将帮助您轻松设计和训练 CNN。
使用 tensorflow 时,您需要将一组图像放入一个 numpy 矩阵中。第一个维度是您的实例,然后是您的图像维度,最后一个维度是 for channels。
因此,例如,如果您使用如下所示的 MNIST 数据,那么您正在使用的灰度图像的尺寸均为 28 x 28。那么您将输入深度学习模型的 numpy 矩阵形状将是 (n, 28, 28 , 1), 其中 是您在数据集中拥有的图像数量。
如何标记图像?
对于大多数数据,标记需要手动完成。这通常被称为数据收集,是任何机器学习解决方案中最困难和最昂贵的部分。通常最好使用现成的数据,或者如果数据不可用,则使用不太复杂的模型和更多的预处理。
这是一个将 CNN 用于 MNIST 数据集的示例
首先我们加载数据
from keras.datasets import mnist
import numpy as np
(x_train, y_train), (x_test, y_test) = mnist.load_data()
x_train = x_train.astype('float32') / 255.
x_test = x_test.astype('float32') / 255.
print('Training data shape: ', x_train.shape)
print('Testing data shape : ', x_test.shape)
训练数据形状:(60000, 28, 28)
测试数据形状:(10000, 28, 28)
from __future__ import print_function
import keras
from keras.datasets import mnist
from keras.models import Sequential
from keras.layers import Dense, Dropout, Flatten
from keras.layers import Conv2D, MaxPooling2D
from keras.callbacks import ModelCheckpoint
from keras.models import model_from_json
from keras import backend as K
然后我们需要重塑我们的数据以在我们的 numpy 矩阵的末尾添加通道维度。此外,我们将对标签进行 one-hot 编码。所以你将有 10 个输出神经元,每个神经元代表一个不同的类。
# The known number of output classes.
num_classes = 10
# Input image dimensions
img_rows, img_cols = 28, 28
# Channels go last for TensorFlow backend
x_train_reshaped = x_train.reshape(x_train.shape[0], img_rows, img_cols, 1)
x_test_reshaped = x_test.reshape(x_test.shape[0], img_rows, img_cols, 1)
input_shape = (img_rows, img_cols, 1)
# Convert class vectors to binary class matrices. This uses 1 hot encoding.
y_train_binary = keras.utils.to_categorical(y_train, num_classes)
y_test_binary = keras.utils.to_categorical(y_test, num_classes)
现在我们设计我们的模型
model = Sequential()
model.add(Conv2D(32, kernel_size=(3, 3),
activation='relu',
input_shape=input_shape))
model.add(Conv2D(64, (3, 3), activation='relu'))
model.add(MaxPooling2D(pool_size=(2, 2)))
model.add(Dropout(0.25))
model.add(Flatten())
model.add(Dense(128, activation='relu'))
model.add(Dropout(0.5))
model.add(Dense(num_classes, activation='softmax'))
model.compile(loss=keras.losses.categorical_crossentropy,
optimizer=keras.optimizers.Adadelta(),
metrics=['accuracy'])
最后我们可以训练模型
epochs = 4
batch_size = 128
# Fit the model weights.
model.fit(x_train_reshaped, y_train_binary,
batch_size=batch_size,
epochs=epochs,
verbose=1,
validation_data=(x_test_reshaped, y_test_binary))
数据集仅由特征和标签组成。这里的特征是你的图像,标签是类。
每个 CNN 模型都有一个 fit() 方法,它将接受特征和标签,并执行训练。
对于第一层,你需要提到图像的输入维度,输出层应该是一个softmax(如果你正在做分类),维度是你拥有的类数。
model = Sequential()
model.add(Conv2D(32, (3, 3), padding='same', input_shape=(64, 64, 3)))
model.add(Activation('relu'))
model.add(Conv2D(32, (3, 3)))
model.add(Activation('relu'))
model.add(MaxPooling2D(pool_size=(2, 2)))
model.add(Dropout(0.25))
model.add(Flatten())
model.add(Dense(512))
model.add(Activation('relu'))
model.add(Dropout(0.5))
model.add(Dense(num_classes))
model.add(Activation('softmax'))
model.compile(loss='categorical_crossentropy', optimizer='Adam', metrics=['accuracy'])
model.fit(x_train, y_train, epochs=10)
以上是训练 Keras 序列模型的代码。
一般要点:
- input_shape 应该是 X_train 的维度。
- 当你做 X_train.shape (numpy) 时你需要得到这个形状
- 然后将卷积与相应的激活一起应用
- Dropout 和 Pooling 层是可选的。
- 在卷积层之后,数据被展平。使用 Flatten()
- 然后它被发送到几个全连接层
- 最后一层应该具有类数的维度
- 最后一层将是softmax。
- 现在,用损失、优化器和度量来编译模型
- 然后拟合()
投票;)如果你喜欢它。
我理解你的问题,我去过那里。确保您收集的数据保存在其各自的类文件夹中,例如,名为“狗”的文件夹中的所有狗图像和“猫”中的猫图像等
我认为可能会有所帮助
IMG_SIZE = 50
DATADIR = 'Path/classes'
CATEGORIES = ['class1 #folder name', 'class2', 'class3']
for category in CATEGORIES :
path = os.path.join(DATADIR, category)
for img in os.listdir(path):
img_array = cv2.imread(os.path.join(path, img), cv2.IMREAD_UNCHANGED)
training_data = []
def create_training_data():
for category in CATEGORIES :
path = os.path.join(DATADIR, category)
class_num = CATEGORIES.index(category)
for img in os.listdir(path):
try :
img_array = cv2.imread(os.path.join(path, img), cv2.IMREAD_UNCHANGED)
new_array = cv2.resize(img_array, (IMG_SIZE, IMG_SIZE))
training_data.append([new_array, class_num])
except Exception as e:
pass
create_training_data()
random.shuffle(training_data)
X = [] #features
y = [] #labels
for features, label in training_data:
X.append(features)
y.append(label)
X = np.array(X).reshape(-1, IMG_SIZE, IMG_SIZE, 3)
y = np.asarray(y)
不是我的代码
向下滚动到准备数据,您将找到创建数据集并将其从计算机导入代码的答案。:)
