import json
import numpy as np
from sklearn.model_selection import train_test_split
import tensorflow.keras as keras
import matplotlib.pyplot as plt

DATASET_PATH = "data.json"

def load_data(dataset_path):
    with open(dataset_path,"r") as fp:
        data = json.load(fp)

    #convert lists in numpy array
    inputs = np.array(data["mfcc"])
    targets = np.array(data["labels"])

    return inputs,targets


def plot_history(history):
    fig, axs = plt.subplots(2)

    #create accuracy subplot
    axs[0].plot(history.history["accuracy"], label ="train accuracy")
    axs[0].plot(history.history["val_accuracy"], label="test accuracy")
    axs[0].set_ylabel("Accuracy")
    axs[0].legend(loc="lower right")
    axs[0].set_title("accuracy eval")

    # create error subplot
    axs[1].plot(history.history["loss"], label="train error")
    axs[1].plot(history.history["val_loss"], label="test error")
    axs[1].set_ylabel("Error")
    axs[1].legend(loc="upper right")
    axs[1].set_title("error eval")

    plt.show()

#load data
inputs, targets = load_data(DATASET_PATH)

#split data into train and test set
inputs_train, inputs_test, targets_train, targets_test = train_test_split(inputs,
                                                                          targets,
                                                                          test_size=0.3)

#build the network architecture
model = keras.models.Sequential()

#input layer
model.add(keras.layers.Flatten(input_shape=(inputs.shape[1], inputs.shape[2])))
#hidden layers
model.add(keras.layers.Dense(512, activation="relu", kernel_regularizer=keras.regularizers.l2(0.001)))
keras.layers.Dropout(0.3)
model.add(keras.layers.Dense(256, activation="relu",kernel_regularizer=keras.regularizers.l2(0.001)))
keras.layers.Dropout(0.3)
model.add(keras.layers.Dense(64, activation="relu",kernel_regularizer=keras.regularizers.l2(0.001)))
keras.layers.Dropout(0.3)
#output layer
model.add(keras.layers.Dense(10, activation="softmax")) #softmax is the activation function for the output layer in classification


#compile the network
optimizer = keras.optimizers.Adam(learning_rate = 0.0001)
model.compile(optimizer = optimizer,
              loss= "sparse_categorical_crossentropy",
              metrics=["accuracy"])
model.summary()


#train the network
history = model.fit(x = inputs_train,
                    y = targets_train,
                    validation_data=(inputs_test,targets_test),
                    epochs = 300,
                    batch_size= 32)

plot_history(history)





