"""
# KMeans- Exercícios
"""
"""
<font color=blue><b> Data Science do Zero</b></font><br>
 www.minerandodados.com.br  
"""
"""
1) Importe as bibliotecas para visualização de dados e clustering.
"""
from sklearn.cluster import KMeans
import pandas as pd
import numpy as np
"""
2) Leia a base de dados **iris.csv** localizada no diretorio **datasets** e crie um Dataframe.
"""
df = pd.read_csv("../input/iris-flower-dataset/IRIS.csv")
df.head()
"""
3) Armazene apenas as **features e seus dados** na variável train.
"""
train = df.species
"""
5) Armazene os dados de classes na variável classes.
"""
classes = df.drop('species', axis=1)
"""
6) Utilizando o código abaixo, crie uma função que faça o **calculo da distância euclidiana entre dois vetores**.
"""
# Função que retorna a distância eucludiana de dois vetores de duas dimensões.
from sklearn.neighbors import DistanceMetric
def calcula_distancia(x,c):
    dist = DistanceMetric.get_metric('euclidean')
    return dist.pairwise(x,c)
"""
7) Utilizando a função **calcula_distancia** faça:
"""
"""
- Calcule a distância entre os vetores **v1 e v2** abaixo
> v1 = [[1.2,1,2.1,1]]<br>
> v2 = [[1,1.9,5.4,3.2]]
"""
v1 = [[1.2,1,2.1,1]]
v2 = [[1,1.9,5.4,3.2]]

calcula_distancia(v1,v2)
"""
- Calcule a distância entre os vetores **v3 e v4** abaixo e explique o retorno
> v3 = [[0.5,0,2.1,1.5]]<br>
> v4 = [[0.5,0,2.1,1.5]]
"""
v3 = [[0.5,0,2.1,1.5]]
v4 = [[0.5,0,2.1,1.5]]

calcula_distancia(v3,v4)
"""
8) Instâncie o algoritmo Kmeans com o número de clusters **igual ao número de classes** da sua base de dados e execute o algoritmo KMeans.
"""
kmeans = KMeans(n_clusters=3)
"""
09) Imprima os valores dos **centroides**.
"""
kmeans.fit(classes)
centros = kmeans.cluster_centers_
centros
"""
10) Selecione **três amostras da base de dados e calcule a distância euclidiana entre as amostras de dados e cada um dos valores de centroids**.
"""
"""
- DICA: Use um laço for...
"""
import random
classes[34:35]
for i in range(1,4):
    num = round(random.uniform(1,50),0)
    num_int = int(num)
    print("Para a amostra de dado número número ", num_int," a distância para os centros é de: ", calcula_distancia(classes[(num_int-1):num_int],centros))
    print("\n")
"""
11) Gere a **tabela de distância** e verifique os valores através do método fit_transform().
"""
distancia = kmeans.fit_transform(classes)
distancia
"""
12) Utilizando o método **predict()** defina novos valores de dados e faça a predição.
"""
import seaborn as sns
"""
Vou gerar os gráficos da distribuição de tamanhos. Assim posso gerar valores aleatorios denrto dessas distribuições para fazer um método predict a partir de dados gerados aleatoriamente.
"""
sns.kdeplot(classes.sepal_length,shade=True )
sns.kdeplot(classes.sepal_width,shade=True )
sns.kdeplot(classes.petal_length,shade=True )
sns.kdeplot(classes.petal_width,shade=True )
X = []
num1 = random.uniform(4,8)
X.append(num1)
num2 = random.uniform(1.5,4.5)
X.append(num2)
num3 = random.uniform(0,8)
X.append(num3)
num4 = random.uniform(0,3)
X.append(num4)
X = np.array(X).reshape(1,4)
X
calcula_distancia(X,centros)
"""
Percebi que o indice 0 corresponde a classe 2, o indice 1 corresponde a classe 0 e o indice 2 corresponde a classe 1. Ao gerar valores aleatorios varias vezes, pode-se ver isso**
"""
print(kmeans.predict(X))
i = 0
while i < 10:
    X = []
    num1 = random.uniform(4,8)
    X.append(num1)
    num2 = random.uniform(1.5,4.5)
    X.append(num2)
    num3 = random.uniform(0,8)
    X.append(num3)
    num4 = random.uniform(0,3)
    X.append(num4)
    X = np.array(X).reshape(1,4)
    print("Dado", i+1, "gerado: ", X,"Distancia para os centros de: ", calcula_distancia(X,centros)," Classificação prevista: ", kmeans.predict(X))
    i = i + 1
"""
Como pode ser visto no while acim. O indice 0 corresponde a classe 2, o indice 1 corresponde a classe 0 e o indice 2 corresponde a classe 1. Ao gerar valores aleatorios varias vezes, pode-se ver isso
"""