Keras混合数据多输入模型训练报错:输入张量数量不匹配求助
多输入模型训练报错问题与解决方案验证
我尝试用Embedding层处理包含分类特征与数值特征的混合数据,采用Kaggle房价数据集保证可复现性,编写的初步代码如下:
from tensorflow.keras.layers import Normalization, Dense, Flatten, Embedding, Input, Reshape, Concatenate, Dropout, Activation import tensorflow as tf import os import pandas as pd import numpy as np from keras.utils import plot_model from IPython.display import Image from keras.models import Sequential, Model # 参考并改编自相关教程 class EmbeddingMapping(): """ 处理分类变量的辅助类 每个分类变量对应一个该类的实例 """ def __init__(self, series, name): # 获取唯一值列表 values = series.unique().tolist() # 建立值到整数的映射字典 self.embedding_dict = {value: int_value + 1 for int_value, value in enumerate(values)} # num_values用于定义Embedding层的input_dim,同时作为未见过值的映射结果 self.num_values = len(values) + 1 self.name = name def get_mapping(self, value): # 训练集中见过的值返回对应的整数映射 if value in self.embedding_dict: return self.embedding_dict[value] # 未见过的值返回统一的整数 else: return self.num_values def get_name(self): return self.name def get_embedding_name(self): return 'embedded_' + self.name def get_embedding_size(self): return int(min(np.ceil((len(self.embedding_dict))/2), 50)) os.chdir("../data") train_data = pd.read_csv("train.csv") target_name = "SalePrice" categorical_features = [ "GarageFinish" # 分类特征 , "Neighborhood" # 分类特征 ] numerical_features = [ "GrLivArea" , "TotalBsmtSF" , "BsmtFinSF1" , "YearRemodAdd" , "YearBuilt" , "GarageCars" , "LotArea" , "1stFlrSF" , "GarageArea" , "Fireplaces" , "2ndFlrSF" , "OverallQual" # 有序分类特征 , "OverallCond" # 有序分类特征 # TODO 将这些有序特征映射为数值 # , "BsmtQual" # 有序分类特征 # , "KitchenQual" # 有序分类特征 ] relevant_columns = [] relevant_columns.extend(categorical_features) relevant_columns.extend(numerical_features) relevant_columns.append(target_name) sub_data = train_data[relevant_columns] embedding_mappings=[] embedding_inputs=[] embeddings=[] for categorical_column in categorical_features: embedding_mapping = EmbeddingMapping(sub_data[categorical_column], categorical_column) input = Input(shape=(1,), dtype='int32') embedding_size=embedding_mapping.get_embedding_size() embedding = Embedding(output_dim=embedding_size, input_dim=embedding_mapping.num_values , input_length=1, name=categorical_column)(input) embedding = Reshape(target_shape=(embedding_size,))(embedding) embedding_mappings.append(embedding_mapping) embedding_inputs.append(input) embeddings.append(embedding) sub_data = sub_data.assign(temp_name=sub_data[categorical_column].apply(embedding_mapping.get_mapping)) sub_data.rename(columns={'temp_name': embedding_mapping.get_embedding_name()}, inplace=True) sub_data.drop(categorical_column, axis = 1, inplace=True) normalisation_inputs=[] normalisations=[] for numerical_feature in numerical_features: input = Input(shape=(1,)) norm = Normalization(name=numerical_feature)(input) normalisation_inputs.append(input) normalisations.append(norm) embeddings.extend(normalisations) embedding_inputs.extend(normalisation_inputs) output = Concatenate()(embeddings) output = Dense(512, kernel_initializer="uniform")(output) output = Activation('relu')(output) output= Dropout(0.4)(output) output = Dense(256, kernel_initializer="uniform")(output) output = Activation('relu')(output) output= Dropout(0.3)(output) output = Dense(1, activation='linear')(output) model = Model(inputs=embedding_inputs, outputs=output) model.compile(loss=tf.keras.losses.MeanAbsolutePercentageError(), optimizer=tf.keras.optimizers.Adam(learning_rate=0.01)) y_train = np.log(sub_data[target_name]) X_train = sub_data.drop(target_name, axis=1) model.fit(X_train, y_train, epochs=10, batch_size=30)
报错信息
训练时触发如下错误:
ValueError: Layer "model_6" expects 15 input(s), but it received 1 input tensors. Inputs received: [<tf.Tensor 'IteratorGetNext:0' shape=(None, 15) dtype=int64>]
模型结构

猜想解决方案
我提出了如下解决方案,希望得到验证:
input_train_list = [] for column in X_train.columns: input_train_list.append(X_train[column ].values) model.fit(input_train_list, y_train, epochs=10, batch_size=30)
内容的提问来源于stack exchange,提问作者cs0815
相关产品推荐
相关产品推荐

