import matplotlib.pyplot as plt
import numpy as np

def gen_data(n, start=0, end=10):
    x = np.linspace(start, end, n)
    y = np.sin(10*x) - x*x
    return y

def gen_data_osc(n):
    return np.array([1024 + (-2)**(-i/100) for i in range(n)])

def gen_data_rand(n):
    return np.random.randn(n) + 0.3*np.linspace(0, 10, n)

def calc_cov(X, Y):
    return np.sum((X - np.average(X))*(Y - np.average(Y))) / (X.shape[0] - 1)

def angular_coef(X,Y):
    return calc_cov(X,Y)/calc_cov(X,X)

def linear_coef(a, X, Y):
    return np.average(Y) - a*np.average(X)

count = 100
end = 100
time = np.linspace(0, end, count)
data = gen_data(count)

delta = end / count

preds = []
kg_preds = []

kg_prediction = 0

for i in range(1, count):
    a = angular_coef(time[:i], data[:i])
    b = linear_coef(a, time[:i], data[:i])

    prediction = (time[i]+delta)*a + b
    preds.append(prediction)

    avg_X = np.average(time[:i])
    avg_Y = np.average(data[:i])
    cov = calc_cov(time[:i], data[:i])

estimate = time*a + b

plt.scatter(time, data, label="Medições", color="#FF5850")
plt.scatter(time[1:], preds, label="Est. Min. Quad.", color="#62B21C")
plt.plot(time, estimate, label="Min. Quad. Final", color="#36A1FF")
plt.xlabel("Tempo")
plt.ylabel("Temperatura")
plt.title("Aproximação Por Minimos Quadrados")
# Place a legend to the right of this smaller subplot.
plt.legend()

plt.show()