Spaces:
Build error
Build error
import pandas as pd | |
import numpy as np | |
import tensorflow as tf | |
import streamlit as st | |
import time | |
#------------------------------------------------------------- | |
# For outputting the final type but in color | |
type_to_color = { | |
'GRASS': "#33FF3F", | |
'FIRE': "#FF4533", | |
'WATER':"#339DFF", | |
'BUG': "#AFFF33", | |
'NORMAL': "#000000", | |
'DARK': "#10081A", | |
'POISON': "#E36DED", | |
'ELECTRIC': "#FCFF2A", | |
'GROUND': "#7F5131", | |
'ICE': "#B3FEFF", | |
'FAIRY': "#FFB3FE", | |
'STEEL': "#6E6E6E", | |
'FIGHTING': "#AB7148", | |
'PSYCHIC': "#A33EBF", | |
'ROCK': "#4A3727", | |
'GHOST': "#DDD2F4", | |
'DRAGON': "#DB8645", | |
'FLYING': "#98E6FF" | |
} | |
#--------------------------------------------------------------------- | |
# Input your X values for prediction (a NumPy array)-------------------- | |
options = ['Type', 'BST', 'HP', 'Attack', 'Defense', 'Sp. Attack', 'Sp. Defense', 'Speed'] | |
# Create the multiselect | |
selected_options = st.multiselect('Select which stats you already have (Pick 2-7):', options) | |
input_feature_length = len(selected_options) | |
while input_feature_length not in range(2,8): | |
time.sleep(0.5) | |
loaded_model = tf.keras.models.load_model(f'Pokemon_Trained_Models/{input_feature_length}feature_model.HDF5') | |
# Initializing a numpy array to house input values | |
X_values = np.zeros((1,int(input_feature_length)+8)) | |
options_to_positions = { | |
'Type': 0, | |
'BST': 1, | |
'HP': 2, | |
'Attack': 3, | |
'Defense': 4, | |
'Sp. Attack': 5, | |
'Sp. Defense': 6, | |
'Speed': 7, | |
} | |
# Reversing the options_to_positions dictionary so I can use it to label output stats | |
reversed_options_to_positions = {v: k for k, v in options_to_positions.items()} | |
# Ordering selected_options numerically based on options_to_positions dictionary | |
selected_options = sorted(selected_options, key=lambda x: options_to_positions[x]) | |
# Adding the indicator vector based on selected stats | |
indicator_positions = [options_to_positions[i] for i in selected_options] | |
for i in indicator_positions: | |
X_values[0, i+input_feature_length] = 1 | |
types_to_numbers = { | |
'GRASS': 0.056, | |
'FIRE': 0.112, | |
'WATER':0.168, | |
'BUG': 0.224, | |
'NORMAL': 0.28, | |
'DARK': 0.336, | |
'POISON': 0.392, | |
'ELECTRIC': 0.448, | |
'GROUND': 0.504, | |
'ICE': 0.56, | |
'FAIRY': 0.616, | |
'STEEL': 0.672, | |
'FIGHTING': 0.728, | |
'PSYCHIC': 0.784, | |
'ROCK': 0.84, | |
'GHOST': 0.896, | |
'DRAGON': 0.952, | |
'FLYING': 1.008 | |
} | |
option_stat_ranges = {'BST': 'BST (175-1125)', 'HP': 'HP (1-255)', 'Attack': 'Attack (5-190)', 'Defense': 'Defense (5-250)', 'Sp. Attack': 'Sp. Attack (10-194)', 'Sp. Defense': 'Sp. Defense (20-250)', 'Speed': 'Speed (5-200)'} | |
pokemon_types = ['GRASS', 'FIRE', 'WATER', 'BUG', 'NORMAL', 'DARK', 'POISON', 'ELECTRIC', 'GROUND', 'ICE', 'FAIRY', 'STEEL', 'FIGHTING', 'PSYCHIC', 'ROCK', 'GHOST', 'DRAGON', 'FLYING'] | |
counter = 0 | |
for i in selected_options: | |
counter += 1 | |
if 'Type' == i: | |
selected_type = st.selectbox('What type is the Pokemon:', pokemon_types) | |
X_values[0, counter-1] = types_to_numbers[selected_type] | |
else: | |
while True: | |
try: | |
X_values[0, counter-1] = st.text_input(f'What is the value for {option_stat_ranges[i]}?') | |
break | |
except Exception: | |
time.sleep(0.5) | |
# Changing 'Type' to 'Type 1' so it fits the name in the .csv file | |
selected_options = ['Type 1' if item == 'Type' else item for item in selected_options] | |
# Define the file path | |
file_path = "pokemon.csv" | |
df = pd.read_csv(file_path) | |
columns_to_delete = ['Dex No', 'Name', 'Base Name', 'Type 2'] | |
df = df.drop(columns=columns_to_delete) | |
#Copy dataframe for future refernce: | |
old_df = df.copy() | |
#Selecting columns that will be scaled | |
values_to_scale = X_values[0, 0:input_feature_length] | |
#Scaling the columns with Min-Max Scaling | |
counter_2 = 0 | |
for stat in selected_options: | |
counter_2 +=1 | |
if stat != 'Type 1': | |
min_value = df[stat].min() | |
max_value = df[stat].max() | |
X_values[0, counter_2-1] = (X_values[0, counter_2-1] - min_value) / (max_value - min_value) | |
#-==================================================================================================================================== | |
# Extract indices of '1' values----------------------------------------- | |
indices_of_ones = [index for index, value in enumerate(X_values[0]) if value == 1] | |
# Changing values so they fit their appropriate column | |
for i in range(len(indices_of_ones)): | |
indices_of_ones[i] -= input_feature_length-1 | |
print("Indices of '1' values:", indices_of_ones) | |
# Use the '1' values to find what the export columns will be--- | |
full_range = list(range(1, 9)) | |
# Find the missing indices by taking the set difference | |
missing_indices = list(set(full_range) - set(indices_of_ones)) | |
missing_indices.sort() | |
print(missing_indices) | |
# Use the model to make predictions------------------------------------- | |
Y_values = loaded_model.predict(X_values) | |
List_Y_values = Y_values[0].tolist() | |
print(f"Raw Output Values: {List_Y_values}") | |
# Initializing 'converted_Y_values' to be same length as 'Y_values' | |
converted_Y_values = [None] * (len(missing_indices)) | |
#_------------ Making values readable (undoing min-max and other scaling) | |
if 1 in indices_of_ones: | |
converted_Y_values = [None] * (len(missing_indices)) | |
#'len(missing_indices)' is the length of the 'missing_indices' | |
for i in range(len(missing_indices)): | |
# Defining Min-Max Values, using the indicies value to match elements | |
min_max_values = { | |
2: [old_df['BST'].min(), old_df['BST'].max()], | |
3: [old_df['HP'].min(), old_df['HP'].max()], | |
4: [old_df['Attack'].min(), old_df['Attack'].max()], | |
5: [old_df['Defense'].min(), old_df['Defense'].max()], | |
6: [old_df['Sp. Attack'].min(), old_df['Sp. Attack'].max()], | |
7: [old_df['Sp. Defense'].min(), old_df['Sp. Defense'].max()], | |
8: [old_df['Speed'].min(), old_df['Speed'].max()] | |
} | |
temp_min_max = min_max_values[missing_indices[i]] | |
# Undo the min-max scaling | |
converted_Y_values[i] = List_Y_values[i] * (temp_min_max[1] - temp_min_max[0]) + temp_min_max[0] | |
else: | |
converted_Y_values = [None] * (len(missing_indices) - 1) | |
# Converting 'Type 1' back to readable type | |
type_output_indicator = True | |
closest_type = None | |
min_difference = float('inf') | |
# Finding closest type for the value | |
for pokemon_type, value in types_to_numbers.items(): | |
difference = abs(Y_values[0,0] - value) | |
if difference < min_difference: | |
min_difference = difference | |
closest_type = pokemon_type | |
# Delete the '1' from missing indices because it's dealt with above | |
del missing_indices[0] | |
del List_Y_values[0] | |
for i in range(len(missing_indices)): | |
# Defining Min-Max Values, using the indicies value to match elements | |
min_max_values = { | |
2: [old_df['BST'].min(), old_df['BST'].max()], | |
3: [old_df['HP'].min(), old_df['HP'].max()], | |
4: [old_df['Attack'].min(), old_df['Attack'].max()], | |
5: [old_df['Defense'].min(), old_df['Defense'].max()], | |
6: [old_df['Sp. Attack'].min(), old_df['Sp. Attack'].max()], | |
7: [old_df['Sp. Defense'].min(), old_df['Sp. Defense'].max()], | |
8: [old_df['Speed'].min(), old_df['Speed'].max()] | |
} | |
temp_min_max = min_max_values[missing_indices[i]] | |
# Undo the min-max scaling | |
converted_Y_values[i] = List_Y_values[i] * (temp_min_max[1] - temp_min_max[0]) + temp_min_max[0] | |
# For making the 'closest_type' text the color of the type | |
color = type_to_color[closest_type] | |
st.write("Output Stats:") | |
if 'closest_type' in vars(): | |
st.write(f"<p style='color: {color};'>Type - {closest_type}</p>", unsafe_allow_html=True) | |
counter_3 = 0 | |
for i in missing_indices: | |
st.write(f"{reversed_options_to_positions[i-1]} - {round(converted_Y_values[counter_3])}") | |
counter_3 +=1 |