如下程序摘自于一本畅销书,你看看有无问题?
python
def create_mlp(shape):
X_input = Input((shape,))
X = Dense(256, activation='relu')(X_input)
X = Dense(128, activation='relu')(X)
X = Dense(64, activation='relu')(X)
X = Dense(1, activation='sigmoid')(X)
model = Model(inputs=X_input, outputs=X)
model.compile(optimizer='adam', loss='binary_crossentropy',
metrics=['accuracy'])
return model
mlp_model = create_mlp(x_train.shape[0])
mlp_model.fit(x=x_train, y=y_train, epochs=30, batch_size=512)
- 关键错误 :
create_mlp(x_train.shape[0])传入的是训练样本的数量(行数),而不是输入特征的维度(列数)。 - 正确用法 :应该传入
x_train.shape[1],即每个样本的特征数量。
在使用神经网络时,shape(形状)是描述数据维度的关键属性,充分理解它是避免该错误的关键。
一、什么是 shape?
shape 是NumPy数组或TensorFlow/PyTorch张量的一个属性,它返回一个元组 ,用来描述数据的维度大小。
shape告诉你数据是几维的,以及每一维有多少个元素。
二、用一个清晰的例子理解 shape
假设我们有一个学生成绩数据集 x_train,它包含了 100名学生 的 5门课程成绩:
| 学生ID | 数学 | 语文 | 英语 | 物理 | 化学 |
|---|---|---|---|---|---|
| 1 | 90 | 85 | 95 | 88 | 92 |
| 2 | 80 | 92 | 88 | 90 | 85 |
| ... | ... | ... | ... | ... | ... |
| 100 | 75 | 88 | 90 | 82 | 89 |
这是一个二维数据 ,包含 100行 和 5列。
在Python中,它的 shape 就是:
python
print(x_train.shape)
# 输出: (100, 5)
- 第一个数字
100:表示数据有 100个样本(100行,对应100名学生)。 - 第二个数字
5:表示每个样本有 5个特征(5列,对应5门课程成绩)。
三、神经网络需要的是哪个维度?
在定义神经网络输入层时,我们需要告诉模型:每个样本有多少个特征?,也就是说将一个样本输入到模型时,模型要接收这个样本所需要变量数。
对于上面的例子,每个学生有 5门课程成绩 ,也就是每个样本有 5个特征 ,所以输入层的形状应该是 (5,)。
正确的做法:
python
# 获取特征数量:shape[1]
input_dim = x_train.shape[1] # 结果是 5
# 定义输入层
X_input = Input(shape=(input_dim,)) # 正确!shape=(5,)
错误的做法:
python
# 获取样本数量:shape[0]
wrong_dim = x_train.shape[0] # 结果是 100
# 定义输入层
X_input = Input(shape=(wrong_dim,)) # 错误!这里的100代表100个特征,而不是100个样本
关键区别:
x_train.shape[0]→ 样本数量(有多少行,有多少个学生)x_train.shape[1]→ 特征数量(每行有多少列,每个学生有多少门课成绩)
在这个例子中,错误地使用 shape[0] 会导致模型期望每个样本有100个特征,而实际上只有5个,这会直接导致模型构建失败或运行时错误,非常容易发现。
四、常见数据集形状详解
上述是针对样本是一维数组的,对应的是特征数量 ,
可扩展到样本是张量情形。常见情形举例如表。
| 数据类型 | 形状示例 | 解释 |
|---|---|---|
| 二维表格数据 | (1000, 10) |
1000个样本,每个样本有10个特征 |
| 灰度图像 | (60000, 28, 28) |
60000张图片,每张图片是28x28像素的二维矩阵 |
| 彩色图像 | (5000, 32, 32, 3) |
5000张图片,每张图片是32x32像素,有RGB三个通道 |
| 序列数据 | (1000, 50, 128) |
1000个序列,每个序列有50个时间步,每个时间步有128个特征 |
样本是一维数组,训练集就是二维数据,通常是基于训练集来说事。即:
- 二维数据 (表格):
shape[1]是特征数 - 三维数据 (灰度图):
shape[1:]是特征形状(如(28, 28)) - 四维数据 (彩色图):
shape[1:]是特征形状(如(32, 32, 3))
避免错误的步骤:
- 打印数据集的
shape看看:print(x_train.shape) - 确定每个样本的特征维度:
- 表格数据:取
shape[1] - 图像数据:取
shape[1:]
- 表格数据:取
- 将这个维度作为输入层的
shape(节点数及布局)。
通过以上方法,你就能从根源上避免输入形状错误,确保模型正确构建和训练。