Turning the number of inputs when I call makeModel from 3 to 1 allows the program to run without errors but no training actually happens and the accuracy doesn’t change.
import pandas as pd from numpy import loadtxt from sklearn.impute import SimpleImputer from sklearn.model_selection import train_test_split from tensorflow.keras.models import Sequential from tensorflow.keras.layers import Dense from sklearn.preprocessing import LabelEncoder from sklearn.utils import shuffle from sklearn.tree import DecisionTreeRegressor as dtr from sklearn.metrics import mean_absolute_error as mae import numpy as np def makeModel(num_inputs, num_classes, train_X, train_y): model = Sequential() model.add(Dense(8, input_dim=num_inputs, activation='relu')) model.add(Dense(10, activation='relu')) model.add(Dense(10, activation='relu')) model.add(Dense(10, activation='relu')) model.add(Dense(3, activation='softmax')) model.compile(loss='categorical_crossentropy', optimizer='adam', metrics=['accuracy']) model.fit(train_X, train_y, epochs=10, batch_size=10) return model label_encoder = LabelEncoder() iris_data = pd.read_csv("iris.csv") iris_data = shuffle(iris_data) iris_data['species'] = label_encoder.fit_transform(iris_data['species']) feature_columns = ['sepal_length', 'sepal_width', 'petal_length', 'petal_width'] X = iris_data[feature_columns] y = iris_data['species'] train_x, val_x, train_y, val_y = train_test_split(X, y, test_size=0.2) iris_model = makeModel(4, 3, train_x, train_y)
Advertisement
Answer
LabelEncoder
transforms the input to an array of encoded values. i.e if your input is ["paris", "paris", "tokyo", "amsterdam"]
then they can be encoded as [0, 0, 1, 2]
. It is not one-hot encoding scheme which is expected by categorical_crossentropy
loss. If you have a integer encoding you will have to use sparse_categorical_crossentropy
Fix
change your code loss to sparse_categorical_crossentropy
:
model.compile(loss='sparse_categorical_crossentropy', optimizer='adam', metrics=['accuracy'])
Sample
def makeModel(num_inputs, num_classes, train_X, train_y): model = Sequential() model.add(Dense(8, input_dim=num_inputs, activation='relu')) model.add(Dense(10, activation='relu')) model.add(Dense(10, activation='relu')) model.add(Dense(10, activation='relu')) model.add(Dense(3, activation='softmax')) model.compile(loss='sparse_categorical_crossentropy', optimizer='adam', metrics=['accuracy']) model.fit(train_X, train_y, epochs=10, batch_size=10) return model label_encoder = LabelEncoder() iris = datasets.load_iris() y = iris.target y = label_encoder.fit_transform(y) train_x, val_x, train_y, val_y = train_test_split(iris.data, y, test_size=0.2) iris_model = makeModel(4, 3, train_x, train_y)