我正在构建一个字符级卷积神经网络。我有一组样本作为训练数据,每个样本的维度为3640。我认为我对如何在tensorflow中调整/重塑维度几乎一无所知,因为我不断遇到无法解决的错误:
Traceback (most recent call last): File "/Users/osopova/Documents/00_KSU_Masters/00_2016_Fall/00_Research/cnn_da/step_4_cnn_4.py", line 87, in my_conv_model prediction, loss = learn.models.logistic_regression(pool, y) File "/Users/osopova/Applications/anaconda/lib/python2.7/site-packages/tensorflow/contrib/learn/python/learn/models.py", line 146, in logistic_regression 'weights', [x.get_shape()[1], y.get_shape()[-1]], dtype=dtype) File "/Users/osopova/Applications/anaconda/lib/python2.7/site-packages/tensorflow/python/ops/variable_scope.py", line 873, in get_variable custom_getter=custom_getter) File "/Users/osopova/Applications/anaconda/lib/python2.7/site-packages/tensorflow/python/ops/variable_scope.py", line 700, in get_variable custom_getter=custom_getter) File "/Users/osopova/Applications/anaconda/lib/python2.7/site-packages/tensorflow/python/ops/variable_scope.py", line 217, in get_variable validate_shape=validate_shape) File "/Users/osopova/Applications/anaconda/lib/python2.7/site-packages/tensorflow/python/ops/variable_scope.py", line 202, in _true_getter caching_device=caching_device, validate_shape=validate_shape) File "/Users/osopova/Applications/anaconda/lib/python2.7/site-packages/tensorflow/python/ops/variable_scope.py", line 515, in _get_single_variable "but instead was %s." % (name, shape))ValueError: Shape of a new variable (logistic_regression/weights) must be fully defined, but instead was (?, 1).Traceback (most recent call last): File "/Users/osopova/Documents/00_KSU_Masters/00_2016_Fall/00_Research/cnn_da/step_4_cnn_4.py", line 175, in <module>Traceback (most recent call last): File "/Users/osopova/Documents/00_KSU_Masters/00_2016_Fall/00_Research/cnn_da/step_4_cnn_4.py", line 87, in my_conv_model prediction, loss = learn.models.logistic_regression(pool, y) File "/Users/osopova/Applications/anaconda/lib/python2.7/site-packages/tensorflow/contrib/learn/python/learn/models.py", line 146, in logistic_regression 'weights', [x.get_shape()[1], y.get_shape()[-1]], dtype=dtype) File "/Users/osopova/Applications/anaconda/lib/python2.7/site-packages/tensorflow/python/ops/variable_scope.py", line 873, in get_variable custom_getter=custom_getter) File "/Users/osopova/Applications/anaconda/lib/python2.7/site-packages/tensorflow/python/ops/variable_scope.py", line 700, in get_variable custom_getter=custom_getter) File "/Users/osopova/Applications/anaconda/lib/python2.7/site-packages/tensorflow/python/ops/variable_scope.py", line 217, in get_variable validate_shape=validate_shape) File "/Users/osopova/Applications/anaconda/lib/python2.7/site-packages/tensorflow/python/ops/variable_scope.py", line 202, in _true_getter caching_device=caching_device, validate_shape=validate_shape) File "/Users/osopova/Applications/anaconda/lib/python2.7/site-packages/tensorflow/python/ops/variable_scope.py", line 515, in _get_single_variable "but instead was %s." % (name, shape))ValueError: Shape of a new variable (logistic_regression/weights) must be fully defined, but instead was (?, 1).
以下是代码:
卷积模型开始:
def my_conv_model(x, y):# 形成形状为batch_size x 1 x N_FEATURES x 1的4d张量x = tf.reshape(x, [-1, 1, N_FEATURES, 1])# 这将提供1 x WINDOW_SIZE的滑动窗口卷积features = tf.contrib.layers.convolution2d(inputs=x, num_outputs=N_FILTERS, kernel_size=[1, WINDOW_SIZE], padding='VALID')# 添加RELU以实现非线性features = tf.nn.relu(features)# 对卷积+Relu的输出进行最大池化pool = tf.nn.max_pool(features, ksize=[1, 1, 2, 1], strides=[1, 1, 2, 1], padding='SAME')print("(1) pool_shape", pool.get_shape()) print("(1) y_shape", y.get_shape()) pool_shape = tf.shape(pool)pool = tf.reshape(pool, [pool_shape[0], pool_shape[2]*pool_shape[3]])y = tf.expand_dims(y, 1)print("(2) pool_shape", pool.get_shape()) print("(2) y_shape", y.get_shape()) try: exc_info = sys.exc_info() print("(3) pool_shape", pool.get_shape()) print("(3) y_shape", y.get_shape())
这里出现错误:
prediction, loss = learn.models.logistic_regression(pool, y) return prediction, lossexcept Exception: #print(traceback.format_exc()) passfinally: # 显示原始异常 traceback.print_exception(*exc_info) del exc_info#return prediction, loss
形状如下:
(1) pool_shape (?, 1, 1819, 10)(1) y_shape (?,)(2) pool_shape (?, ?)(2) y_shape (?, 1)(3) pool_shape (?, ?)(3) y_shape (?, 1)
主函数如下:
def main(unused_argv): # 训练和测试数据编码为one-hot data_folder = './data' sandyData = np.loadtxt(data_folder+'/sandyData.csv', delimiter=',') sandyLabels = np.loadtxt(data_folder+'/sandyLabels.csv', delimiter=',') x_train, x_test, y_train, y_test = \ train_test_split(sandyData, sandyLabels, test_size=0.2, random_state=7) x_train = np.array(x_train, dtype=np.float32) x_test = np.array(x_test, dtype=np.float32) y_train = np.array(y_train, dtype=np.float32) y_test = np.array(y_test, dtype=np.float32) # 构建模型 classifier = learn.Estimator(model_fn=my_conv_model) # 训练和预测 classifier.fit(x_train, y_train, steps=100) y_predicted = [p['class'] for p in classifier.predict(x_test, as_iterable=True)] score = metrics.accuracy_score(y_test, y_predicted) print('Accuracy: {0:f}'.format(score))if __name__ == '__main__': tf.app.run() `
回答:
看起来问题出在传递给logistic_regression()
的pool
参数没有已知的列数。linear_regression()
需要知道其x
参数的列数,以便创建大小合适的权重矩阵。
这个问题源自以下行:
pool_shape = tf.shape(pool)pool = tf.reshape(pool, [pool_shape[0], pool_shape[2]*pool_shape[3]])
尽管pool_shape[2]*pool_shape[3]
具有常量值,但TensorFlow的客户端常量折叠当前不处理此表达式,因此它推断出pool
张量的静态形状为(?, ?)
(如您的日志输出所示)。一个解决方法是进行以下更改:
pool_shape = pool.get_shape()pool = tf.reshape(pool, [-1, (pool_shape[2] * pool_shape[3]).value])
使用pool.get_shape()
而不是tf.shape(pool)
可以为TensorFlow提供更多关于pool
的(部分定义的)形状的信息,作为tf.TensorShape
对象而不是tf.Tensor
对象。在此更改之后,pool_shape[2]
和pool_shape[3]
都具有已知值,因此pool
的列数将是已知的。