在Tensorflow中使用功能性Api会引发KeyError:'input_1'

时间:2020-05-25 01:03:11

标签: python tensorflow

我正在尝试使用TensorFlow功能API构建简单的线性模型。

def create_model():
    input1 = tf.keras.Input(shape=(30,))
    hidden1 = tf.keras.layers.Dense(units = 12, activation='relu')(input1)
    hidden2 = tf.keras.layers.Dense(units = 6, activation='relu')(hidden1)
    output1 = tf.keras.layers.Dense(units = 2, activation='softmax')(hidden2)
    model = tf.keras.models.Model(inputs = input1, outputs = output1)
    model.compile(optimizer='adam',
                  loss='sparse_categorical_crossentropy',
                  metrics=['accuracy'])
    return model

这是我创建模型的代码。
我正在使用数据管道来创建这样的输入数据集。

def make_dataset(dataframe, shuffle=True, batch_size=32):
    labels = dataframe.pop('target')
    ds = tf.data.Dataset.from_tensor_slices((dict(dataframe), labels))
    if shuffle:
        ds = ds.shuffle(buffer_size=100000, seed = 121 ).repeat()
    return ds
pos_ds = make_dataset(train_data_pos)
neg_ds = make_dataset(train_data_neg)
train_ds = tf.data.experimental.sample_from_datasets([pos_ds, neg_ds], weights=[0.5, 0.5], seed = 45)
train_ds = train_ds.batch(BATCH_SIZE)
steps_per_epoch = np.ceil(2.0*count_neg/BATCH_SIZE)

这是train_data_pos和train_data_neg是包含正负类的数据框

history = model.fit(train_ds,
          validation_data=val_ds,
          epochs=100,
          verbose = 1,
          steps_per_epoch=steps_per_epoch)

这是我的model.fit()cmd。

我的错误日志如下:

Traceback (most recent call last):
  File "6.py", line 159, in <module>
    steps_per_epoch=steps_per_epoch)
  File "C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\keras\engine\training.py", line 66, in _method_wrapper
    return method(self, *args, **kwargs)
  File "C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\keras\engine\training.py", line 848, in fit
    tmp_logs = train_function(iterator)
  File "C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\eager\def_function.py", line 580, in __call__
    result = self._call(*args, **kwds)
  File "C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\eager\def_function.py", line 627, in _call
    self._initialize(args, kwds, add_initializers_to=initializers)
  File "C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\eager\def_function.py", line 506, in _initialize
    *args, **kwds))
  File "C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\eager\function.py", line 2446, in _get_concrete_function_internal_garbage_collected
    graph_function, _, _ = self._maybe_define_function(args, kwargs)
  File "C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\eager\function.py", line 2777, in _maybe_define_function
    graph_function = self._create_graph_function(args, kwargs)
  File "C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\eager\function.py", line 2667, in _create_graph_function
    capture_by_value=self._capture_by_value),
  File "C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\framework\func_graph.py", line 981, in func_graph_from_py_func
    func_outputs = python_func(*func_args, **func_kwargs)
  File "C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\eager\def_function.py", line 441, in wrapped_fn
    return weak_wrapped_fn().__wrapped__(*args, **kwds)
  File "C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\framework\func_graph.py", line 968, in wrapper
    raise e.ag_error_metadata.to_exception(e)
tensorflow.python.autograph.pyct.error_utils.KeyError: in user code:

    C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\keras\engine\training.py:571 train_function  *
        outputs = self.distribute_strategy.run(
    C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\distribute\distribute_lib.py:951 run  **
        return self._extended.call_for_each_replica(fn, args=args, kwargs=kwargs)
    C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\distribute\distribute_lib.py:2290 call_for_each_replica
        return self._call_for_each_replica(fn, args, kwargs)
    C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\distribute\distribute_lib.py:2649 _call_for_each_replica
        return fn(*args, **kwargs)
    C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\keras\engine\training.py:531 train_step  **
        y_pred = self(x, training=True)
    C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\keras\engine\base_layer.py:927 __call__
        outputs = call_fn(cast_inputs, *args, **kwargs)
    C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\keras\engine\network.py:719 call
        convert_kwargs_to_constants=base_layer_utils.call_context().saving)
    C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\keras\engine\network.py:826 _run_internal_graph
        inputs = self._flatten_to_reference_inputs(inputs)
    C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\keras\engine\network.py:926 _flatten_to_reference_inputs
        return [tensors[inp._keras_history.layer.name] for inp in ref_inputs]
    C:\Users\Aniket\Documents\Aniket\learning-ML\ML_env\lib\site-packages\tensorflow\python\keras\engine\network.py:926 <listcomp>
        return [tensors[inp._keras_history.layer.name] for inp in ref_inputs]

    KeyError: 'input_1'

当我使用顺序API来构建模型时,所有这些方法均有效。

def create_model():
    model = tf.keras.Sequential([
    feature_layer,
    tf.keras.layers.Dense(units = 12, activation='relu', use_bias = True, kernel_initializer= 'glorot_uniform', bias_initializer = 'glorot_uniform', name = 'd1'),
    tf.keras.layers.Dense(units = 6, activation='relu', use_bias = True, kernel_initializer= 'glorot_uniform', bias_initializer = 'glorot_uniform', name = 'd2'),
    tf.keras.layers.Dense(units = 2, activation='softmax', name = 'out')
    ])
    model.compile(optimizer='adam',
                  loss='sparse_categorical_crossentropy',
                  metrics=['accuracy'])
    return model  

feature_layer是 tf.keras.layers.DenseFeatures

以下是整个代码的链接-LINK

1 个答案:

答案 0 :(得分:1)

由于要素列与tf.keras.Input不直接兼容,因此必须使用变通方法将tf.keras.Input分配给每个原始要素列。通过this Github issue的解决方法是:

from __future__ import absolute_import, division, print_function

import numpy as np
import pandas as pd

import tensorflow as tf

from tensorflow import feature_column
from tensorflow import keras
from tensorflow.keras import layers
from sklearn.model_selection import train_test_split

URL = 'https://storage.googleapis.com/applied-dl/heart.csv'
dataframe = pd.read_csv(URL)
dataframe.head()

train, test = train_test_split(dataframe, test_size=0.2)
train, val = train_test_split(train, test_size=0.2)
print(len(train), 'train examples')
print(len(val), 'validation examples')
print(len(test), 'test examples')

# A utility method to create a tf.data dataset from a Pandas Dataframe
def df_to_dataset(dataframe, shuffle=True, batch_size=32):
  dataframe = dataframe.copy()
  labels = dataframe.pop('target')
  ds = tf.data.Dataset.from_tensor_slices((dict(dataframe), labels))
  if shuffle:
    ds = ds.shuffle(buffer_size=len(dataframe))
  ds = ds.batch(batch_size)
  return ds

batch_size = 5 # A small batch sized is used for demonstration purposes
train_ds = df_to_dataset(train, batch_size=batch_size)
val_ds = df_to_dataset(val, shuffle=False, batch_size=batch_size)
test_ds = df_to_dataset(test, shuffle=False, batch_size=batch_size)

def create_inputs():
    age = feature_column.numeric_column("age")

    feature_columns = []
    feature_layer_inputs = {}

    # numeric cols
    for header in ['age', 'trestbps', 'chol', 'thalach', 'oldpeak', 'slope', 'ca']:
        feature_columns.append(feature_column.numeric_column(header))
        feature_layer_inputs[header] = tf.keras.Input(shape=(1,), name=header)

    # bucketized cols
    age_buckets = feature_column.bucketized_column(age, boundaries=[18, 25, 30, 35, 40, 45, 50, 55, 60, 65])
    feature_columns.append(age_buckets)

    # indicator cols
    thal = feature_column.categorical_column_with_vocabulary_list(
      'thal', ['fixed', 'normal', 'reversible'])
    thal_one_hot = feature_column.indicator_column(thal)
    feature_columns.append(thal_one_hot)
    feature_layer_inputs['thal'] = tf.keras.Input(shape=(1,), name='thal', dtype=tf.string)

    # embedding cols
    thal_embedding = feature_column.embedding_column(thal, dimension=8)
    feature_columns.append(thal_embedding)

    # crossed cols
    crossed_feature = feature_column.crossed_column([age_buckets, thal], hash_bucket_size=1000)
    crossed_feature = feature_column.indicator_column(crossed_feature)
    feature_columns.append(crossed_feature)

    return feature_columns, feature_layer_inputs

def create_model():
    feature_columns, feature_layer_inputs = create_inputs()
    dense_features = tf.keras.layers.DenseFeatures(feature_columns)(feature_layer_inputs)
    hidden1 = tf.keras.layers.Dense(units = 12, activation='relu')(dense_features)
    hidden2 = tf.keras.layers.Dense(units = 6, activation='relu')(hidden1)
    output1 = tf.keras.layers.Dense(units = 2, activation='softmax')(hidden2)
    model = tf.keras.models.Model(
        inputs = [v for v in feature_layer_inputs.values()],
        outputs = output1)
    model.compile(optimizer='adam',
        loss='sparse_categorical_crossentropy', metrics=['accuracy'])
    return model

model = create_model()

model.fit(train_ds)
相关问题