Spaces:
Sleeping
Sleeping
#%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% | |
# 1) IMPORTAÇÃO DAS BIBLIOTECAS | |
#%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% | |
import pandas as pd | |
import gradio as gr | |
from gradio import components | |
from gradio import Interface | |
import numpy as np | |
import statsmodels | |
import statsmodels.api as sm | |
from statsmodels.stats.stattools import jarque_bera | |
import plotly.express as px | |
import plotly.graph_objects as go | |
import matplotlib.pyplot as plt | |
import seaborn as sns | |
import sklearn | |
from sklearn.preprocessing import MinMaxScaler | |
from sklearn.ensemble import ExtraTreesRegressor | |
import xlsxwriter | |
from docx import Document | |
from docx.shared import Pt | |
from docx.enum.text import WD_PARAGRAPH_ALIGNMENT | |
from docx.shared import Inches | |
from num2words import num2words | |
from datetime import datetime | |
#%matplotlib inline | |
#%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% | |
# 2) FUNÇÕES ACESSÓRIAS | |
#%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% | |
# função para conversão da escala das variáveis: | |
def aplicar_operacao(df, scv, col_index): | |
if scv == 'x' or scv == '-': | |
pass | |
elif scv == 'lnx': | |
df.iloc[:, col_index] = round(np.log(df.iloc[:, col_index]), 8) | |
elif scv == '1/x': | |
df.iloc[:, col_index] = round(1 / df.iloc[:, col_index], 8) | |
elif scv == 'x²': | |
df.iloc[:, col_index] = round(df.iloc[:, col_index] ** 2, 8) | |
elif scv == 'y': | |
pass | |
elif scv == 'lny': | |
df.iloc[:, col_index] = round(np.log(df.iloc[:, col_index]), 8) | |
elif scv == '1/y': | |
df.iloc[:, col_index] = round(1 / df.iloc[:, col_index], 8) | |
elif scv == 'y²': | |
df.iloc[:, col_index] = round(df.iloc[:, col_index] ** 2, 8) | |
# função para renomear as colunas com as escalas: | |
def renomeia_colunas(df_dados, posicao_coluna, scv): | |
if posicao_coluna < len(df_dados.columns): | |
old_column_name = df_dados.columns[posicao_coluna] | |
new_column_name = old_column_name # Inicializa com o mesmo nome da coluna original | |
if scv == 'x': | |
pass | |
elif scv == '-': | |
pass | |
elif scv == 'lnx': | |
new_column_name = 'ln(' + old_column_name + ')' | |
elif scv == '1/x': | |
new_column_name = '1/(' + old_column_name + ')' | |
elif scv == 'x²': | |
new_column_name = '(' + old_column_name + ')²' | |
if scv == 'y': | |
pass | |
elif scv == 'lny': | |
new_column_name = 'ln(' + old_column_name + ')' | |
elif scv == '1/y': | |
new_column_name = '1/(' + old_column_name + ')' | |
elif scv == 'y²': | |
new_column_name = '(' + old_column_name + ')²' | |
df_dados.rename(columns={old_column_name: new_column_name}, inplace=True) | |
# função para plotagem dos gráficos de dispersão: | |
def criar_grafico_dispersao(df, x_column, y_column, hover_name, trendline_color): | |
# Calculando a correlação entre as variáveis x e y | |
correlacao = df[x_column].corr(df[y_column]) | |
# Criando o gráfico de dispersão com a linha de tendência | |
fig = px.scatter(df, x=x_column, y=y_column, hover_name=hover_name, trendline="ols", height=250) | |
# Definindo a cor de fundo e do papel | |
fig.update_layout( | |
plot_bgcolor='rgb(240, 240, 240)', | |
paper_bgcolor='rgb(240, 240, 240)', | |
showlegend=False | |
) | |
# Definindo a cor dos pontos | |
fig.update_traces(marker=dict(color=trendline_color, size=5)) | |
# Definindo a cor da linha de tendência | |
fig.update_traces(line=dict(color="black")) | |
# Adicionando o texto com a correlação na linha de tendência | |
fig.add_annotation( | |
x=df[x_column].max(), | |
y=df[y_column].max(), | |
text=f"Correlação: {correlacao:.2f}", | |
showarrow=False, | |
font=dict(color="black") | |
) | |
return fig | |
# função que cria uma coluna cos as extrapolações | |
def calc_extrapola(df_1, df_2): | |
# Inicializar a coluna 'extrapola' com strings vazias | |
df_1['extrapola'] = "" | |
for col in df_1.columns[:-1]: # Excluir a coluna 'extrapola' da iteração | |
if col in df_2.columns: # Verifica se a coluna existe nos limites | |
# Acessa os valores de limite direto por posição na coluna correspondente | |
min_val = df_2[col][0] | |
max_val = df_2[col][1] | |
# Cálculo de extrapolação para cada coluna | |
temp_extrapola = df_1[col].apply( | |
lambda x: f"{col}: +{((x - max_val) / max_val) * 100:.2f}%" if x > 2 * max_val else | |
f"{col}: -{((min_val - x) / min_val) * 100:.2f}%" if min_val != 0 and x < 0.5 * min_val else "" | |
) | |
# Concatenar informações de extrapolação na coluna 'extrapola' com verificação para adicionar espaço | |
df_1['extrapola'] = df_1.apply( | |
lambda row: row['extrapola'] + (" " if row['extrapola'] else "") + temp_extrapola[row.name] if temp_extrapola[row.name] else row['extrapola'], | |
axis=1 | |
) | |
# Remove o espaço extra no final de cada entrada e trata casos onde não há extrapolação | |
df_1['extrapola'] = df_1['extrapola'].str.rstrip() | |
# Preenche as células sem extrapolação com "sem extrapolação" | |
df_1.loc[df_1['extrapola'] == '', 'extrapola'] = 'sem extrapolação' | |
return df_1 | |
#%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% | |
#%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% | |
# 3) FUNÇÃO PRINCIPAL P/ GERAÇÃO DO MODELO | |
#%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% | |
#%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% | |
# função para a regressão linear | |
def gera_model(planilha, model, name_model, v_d, scv_d, | |
scv_1, scv_2, scv_3, scv_4, | |
scv_5, scv_6, scv_7, scv_8, | |
scv_9, scv_10, scv_11, scv_12, | |
scv_13, scv_14, scv_15, scv_16, | |
out, | |
laudo="-",data_ref=None, data_laudo=None, | |
nome="-", prof="-", ent="-", uf="RS", reg="-", | |
lograd="-", munic="-", tipo_imo="-", solic="-", finalidade="-", objetivo="-", press="-", | |
infra="Água Potável", serv="Coleta de Lixo", uso="Residencial", pad_reg="-", tipo_via="-", obs_gerais="-", | |
per="Sem destaque", ofe="Sem destaque", liq="Sem destaque", dia="-"): | |
#ooooooooooooooooooooooooooooooooooooooooooooooooooo CARREGAR oooooooooooooooooooooooooooooooooooooooooooooooooooo# | |
# Criação das listas para as colunas | |
svc_list = ['scv_d', 'scv_1', 'scv_2', 'scv_3', 'scv_4', 'scv_5', 'scv_6', 'scv_7', | |
'scv_8', 'scv_9', 'scv_10', 'scv_11', 'scv_12', 'scv_13', 'scv_14', 'scv_15', 'scv_16'] | |
var_dep = [v_d, '-', '-', '-', '-', '-', '-', '-', | |
'-', '-', '-', '-', '-', '-', '-', '-', '-'] | |
escalas_list = [scv_d, scv_1, scv_2, scv_3, scv_4, scv_5, scv_6, scv_7, | |
scv_8, scv_9, scv_10, scv_11, scv_12, scv_13, scv_14, scv_15, scv_16] | |
# Criando o DataFrame com as colunas 'svc' e 'escalas' | |
df_scv = pd.DataFrame({ | |
'svc': svc_list, | |
'escalas': escalas_list, | |
'var_dep': var_dep | |
}) | |
#ooooooooooooooooooooooooooooooooooooooooooooooooooo CARREGAR oooooooooooooooooooooooooooooooooooooooooooooooooooo# | |
# IMPORTRAÇÃO DA PLANILHA | |
# Carregando os dados | |
df_dados = pd.read_excel(planilha.name) | |
df_dados = df_dados.round(4) | |
# Convertendo os cabeçalhos para strings | |
df_dados.columns = [str(col) for col in df_dados.columns] | |
# Convertendo as colunas onde estão o valor total e o valor unitário para float | |
df_dados[df_dados.columns[1]] = df_dados[df_dados.columns[1]].astype(float) | |
df_dados[df_dados.columns[2]] = df_dados[df_dados.columns[2]].astype(float) | |
df_original = df_dados.copy() ################################### OUTPUT ########################################## | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 1: | |
# Criação do "df_avalia" para extrair o "df_limites_var" e o "df_dados_utilizados" por meio da seleção de variáveis | |
# Motivo: necessidade de extração tanto dos nomes das variáveis quanto dos limites a partir do dataframe inicial. | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Dataframe para criação de uma planilha de modelo para avaliação | |
df_avalia = pd.DataFrame() | |
#ooooooooooooooooooooooooooooooooooooooooooooooooooo CARREGAR oooooooooooooooooooooooooooooooooooooooooooooooooooo# | |
if model == "Carregar": | |
# Carrega o arquivo Excel da planilha fornecida (ignorando o cabeçalho na primeira linha) | |
df_escalas = pd.read_excel(planilha.name, sheet_name="Escalas") | |
# Preenchendo as variáveis com base nos valores da planilha, ajustando para o cabeçalho | |
v_d = df_escalas.iloc[0, 2] | |
scv_d = df_escalas.iloc[0, 1] | |
scv_1 = df_escalas.iloc[1, 1] | |
scv_2 = df_escalas.iloc[2, 1] | |
scv_3 = df_escalas.iloc[3, 1] | |
scv_4 = df_escalas.iloc[4, 1] | |
scv_5 = df_escalas.iloc[5, 1] | |
scv_6 = df_escalas.iloc[6, 1] | |
scv_7 = df_escalas.iloc[7, 1] | |
scv_8 = df_escalas.iloc[8, 1] | |
scv_9 = df_escalas.iloc[9, 1] | |
scv_10 = df_escalas.iloc[10, 1] | |
scv_11 = df_escalas.iloc[11, 1] | |
scv_12 = df_escalas.iloc[12, 1] | |
scv_13 = df_escalas.iloc[13, 1] | |
scv_14 = df_escalas.iloc[14, 1] | |
scv_15 = df_escalas.iloc[15, 1] | |
scv_16 = df_escalas.iloc[16, 1] | |
#ooooooooooooooooooooooooooooooooooooooooooooooooooo CARREGAR oooooooooooooooooooooooooooooooooooooooooooooooooooo# | |
# Iterar sobre as colunas do DataFrame df_filtrado | |
for i, col in enumerate(df_dados.columns): | |
# Verificar se a coluna atual deve ser adicionada com base na condição e se ela existe no DataFrame | |
if (i == 3 and scv_1 != "-") or \ | |
(i == 4 and scv_2 != "-") or \ | |
(i == 5 and scv_3 != "-") or \ | |
(i == 6 and scv_4 != "-") or \ | |
(i == 7 and scv_5 != "-") or \ | |
(i == 8 and scv_6 != "-") or \ | |
(i == 9 and scv_7 != "-") or \ | |
(i == 10 and scv_8 != "-") or \ | |
(i == 11 and scv_9 != "-") or \ | |
(i == 12 and scv_10 != "-") or \ | |
(i == 13 and scv_11 != "-") or \ | |
(i == 14 and scv_12 != "-") or \ | |
(i == 15 and scv_13 != "-") or \ | |
(i == 16 and scv_14 != "-") or \ | |
(i == 17 and scv_15 != "-") or \ | |
(i == 18 and scv_16 != "-"): | |
if i < len(df_dados.columns): | |
df_avalia[col] = df_dados.iloc[:, i] | |
# Dataframe para os valores máximos e mínimos por variável | |
# Adicionar a coluna de índice 0 de df_dados em df_avalia (para comparação com os outliers) | |
df_limites_var = df_avalia.copy() | |
df_limites_var[df_dados.columns[0]] = df_dados.iloc[:, 0] | |
# Dataframe para os dados efeticamente utilizados sem conversão de escala | |
df_dados_utilizados = df_avalia.copy() | |
# Obter o nome e os dados da primeira coluna de df_dados | |
first_column_name = df_dados.columns[0] | |
first_column_data = df_dados.iloc[:, 0] | |
# Inserir a nova coluna no início de df_dados_utilizados | |
df_dados_utilizados.insert(0, first_column_name, first_column_data) | |
# NOME DAS VARIÁVEIS | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 2: | |
# Utiliza o "df_original" que é uma cópia do df_dados para criar uma lista com os nomes das colunas originais | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Obtenha os nomes das colunas, excluindo a primeira ou a segunda | |
if v_d == "Valor total": | |
nomes_colunas = df_original.drop(columns=[df_original.columns[0], df_original.columns[2]]).columns | |
else: | |
nomes_colunas = df_original.drop(columns=[df_original.columns[0], df_original.columns[1]]).columns | |
# Crie a lista de strings com os cabeçalhos formatados, incluindo os valores mínimos e máximos | |
colunas = [f'Var dependente = {nomes_colunas[0]}'] | |
for i, coluna in enumerate(nomes_colunas[1:], start=1): | |
min_val = df_original[coluna].min() | |
max_val = df_original[coluna].max() | |
valores_unicos = df_original[coluna].unique() | |
# Verifica se os valores únicos são apenas 0 e 1 | |
if set(valores_unicos).issubset({0, 1}): | |
colunas.append(f'Var {i} = {coluna} (Min: {min_val}, Max: {max_val}) - dicotômica - somente escala "x"') | |
else: | |
colunas.append(f'Var {i} = {coluna} (Min: {min_val}, Max: {max_val})') | |
# Transformando a lista em uma string separada por vírgula | |
string_colunas = "\n".join(colunas)################################### OUTPUT ########################################## | |
# CONVERSÃO DE ESCALAS | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 3: | |
# Utiliza o "df_dados" para aplicar a função de conversão das escalas | |
# -----------------------------------------------------------------------------------------------------------------# | |
# dados | |
if v_d == "Valor total": | |
aplicar_operacao(df_dados, scv_d, 1) | |
else: | |
aplicar_operacao(df_dados, scv_d, 2) | |
aplicar_operacao(df_dados, scv_1, 3) | |
aplicar_operacao(df_dados, scv_2, 4) | |
aplicar_operacao(df_dados, scv_3, 5) | |
aplicar_operacao(df_dados, scv_4, 6) | |
aplicar_operacao(df_dados, scv_5, 7) | |
aplicar_operacao(df_dados, scv_6, 8) | |
aplicar_operacao(df_dados, scv_7, 9) | |
aplicar_operacao(df_dados, scv_8, 10) | |
aplicar_operacao(df_dados, scv_9, 11) | |
aplicar_operacao(df_dados, scv_10, 12) | |
aplicar_operacao(df_dados, scv_11, 13) | |
aplicar_operacao(df_dados, scv_12, 14) | |
aplicar_operacao(df_dados, scv_13, 15) | |
aplicar_operacao(df_dados, scv_14, 16) | |
aplicar_operacao(df_dados, scv_15, 17) | |
aplicar_operacao(df_dados, scv_16, 18) | |
# RENOMEAR OS CABEÇALHOS DAS COLUNAS | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 4: | |
# Utiliza o "df_dados" para aplicar a função que renomeia as colunas conforme a escala utilizada | |
# -----------------------------------------------------------------------------------------------------------------# | |
#dados | |
if v_d == "Valor total": | |
renomeia_colunas(df_dados, 1, scv_d) | |
else: | |
renomeia_colunas(df_dados, 2, scv_d) | |
renomeia_colunas(df_dados, 3, scv_1) | |
renomeia_colunas(df_dados, 4, scv_2) | |
renomeia_colunas(df_dados, 5, scv_3) | |
renomeia_colunas(df_dados, 6, scv_4) | |
renomeia_colunas(df_dados, 7, scv_5) | |
renomeia_colunas(df_dados, 8, scv_6) | |
renomeia_colunas(df_dados, 9, scv_7) | |
renomeia_colunas(df_dados, 10, scv_8) | |
renomeia_colunas(df_dados, 11, scv_9) | |
renomeia_colunas(df_dados, 12, scv_10) | |
renomeia_colunas(df_dados, 13, scv_11) | |
renomeia_colunas(df_dados, 14, scv_12) | |
renomeia_colunas(df_dados, 15, scv_13) | |
renomeia_colunas(df_dados, 16, scv_14) | |
renomeia_colunas(df_dados, 17, scv_15) | |
renomeia_colunas(df_dados, 18, scv_16) | |
# MANIPULAÇÃO DAS LINHAS - RETIRADA DOS OUTLIERS | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 5: | |
# 1) Criar os "dados_out" que são os dados removidos (é a caixa de texto de remoção dos dados na interface) | |
# 2) Cria o datafre de outliers, "df_outliers" excluindo os "dados_out" | |
# 3) Remove do dataframe "df_limites_var" os outliers para chegar num novo "df_limites_var" e nos máximos e mínimos | |
# 4) O "df_dados_utilizados" busca retirar os outliers do dataframe inicial (ver Comenário 1) | |
# 5) Criação do "df_filtrado" a partir da retirada dos outliers do "df_dados" | |
# 6) Contagem final da quantidade de linhas do "df_outliers" | |
# -----------------------------------------------------------------------------------------------------------------# | |
if model == "Carregar": | |
# Carrega o arquivo Excel da planilha fornecida | |
df_nao_utilizados = pd.read_excel(planilha.name, sheet_name="Dados Não utilizados") | |
# Converte o DataFrame da aba "Dados Não Utilizados" para uma lista de valores da primeira coluna | |
out = df_nao_utilizados.iloc[:, 0].values.tolist() # Apenas a primeira coluna | |
# Transformar a lista em uma string separada por vírgulas | |
concatenated_data = ",".join([str(item) for item in out if pd.notna(item)]) | |
# Convertendo a entrada concatenada em uma lista de números inteiros | |
dados_out = [] | |
for num in concatenated_data.split(","): | |
num = num.strip() | |
if num: # Verifica se não é uma string vazia | |
try: | |
# Tenta converter para inteiro | |
dados_out.append(int(float(num))) | |
except ValueError: | |
pass # Ignora valores que não podem ser convertidos | |
else: | |
# Convertendo a entrada manual em uma lista de inteiros | |
dados_out = [int(num.strip()) for num in out.split(",") if num.strip()] | |
# Filtrando o DataFrame para obter os outliers | |
df_outliers = df_dados[df_dados.iloc[:, 0].isin(dados_out)] | |
# Removendo os outliers do DataFrame df_limites_var para calcular os valores mínimos e máximos de cada variável | |
df_limites_var = df_limites_var[~df_dados.iloc[:, 0].isin(dados_out)] | |
# Selecionar colunas excluindo a primeira coluna (índice 0) | |
limites = df_limites_var.columns[:-1] | |
# Calcular o valor mínimo e máximo para cada coluna selecionada | |
minimos = df_limites_var[limites].min() | |
maximos = df_limites_var[limites].max() | |
# Criar o DataFrame df_limites_var com os valores mínimos e máximos | |
df_limites_var = pd.DataFrame({'Min': minimos, 'Max': maximos}) | |
# Se desejar transpor para que as colunas sejam 'Min' e 'Max', e os índices sejam as colunas originais do df_dados | |
df_limites_var_final = df_limites_var.transpose() | |
#df_limites_var_final.to_excel("df_limites_var_final.xlsx", index=False) #################### OUTPUT ################## | |
# Removendo os outliers do Dataframe para os dados efeticamente utilizados sem conversão de escala | |
df_dados_utilizados = df_dados_utilizados[~df_dados.iloc[:, 0].isin(dados_out)] | |
# Removendo os outliers do DataFrame original mas que teve escalas convertidas (este será trabalhado até a regressão) | |
df_filtrado = df_dados[~df_dados.iloc[:, 0].isin(dados_out)] | |
#df_filtrado.to_excel("df_filtrado.xlsx", index=False) #################### Linha de verificação ##################### | |
# Resetando o índice de ambos os DataFrames | |
df_filtrado.reset_index(drop=True, inplace=True) | |
df_outliers.reset_index(drop=True, inplace=True) ############################### OUTPUT ############################## | |
# Contagem de linhas no DataFrame resultante | |
num_outliers = df_outliers.shape[0] | |
# GRÁFICOS DE DISPERSÃO | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 6: | |
# Gráficos de dispersão por variável para análise inicial de pontos discrepantes | |
# -----------------------------------------------------------------------------------------------------------------# | |
fig_v1 = None | |
fig_v2 = None | |
fig_v3 = None | |
fig_v4 = None | |
fig_v5 = None | |
fig_v6 = None | |
fig_v7 = None | |
fig_v8 = None | |
fig_v9 = None | |
fig_v10 = None | |
fig_v11 = None | |
fig_v12 = None | |
fig_v13 = None | |
fig_v14 = None | |
fig_v15 = None | |
fig_v16 = None | |
#################### OUTPUT ################## | |
if scv_1 != "-": | |
if v_d == "Valor total": | |
fig_v1 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[3], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v1 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[3], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
if scv_2 != "-": | |
if v_d == "Valor total": | |
fig_v2 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[4], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v2 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[4], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
if scv_3 != "-": | |
if v_d == "Valor total": | |
fig_v3 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[5], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v3 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[5], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
if scv_4 != "-": | |
if v_d == "Valor total": | |
fig_v4 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[6], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v4 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[6], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
if scv_5 != "-": | |
if v_d == "Valor total": | |
fig_v5 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[7], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v5 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[7], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
if scv_6 != "-": | |
if v_d == "Valor total": | |
fig_v6 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[8], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v6 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[8], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
if scv_7 != "-": | |
if v_d == "Valor total": | |
fig_v7 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[9], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v7 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[9], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
if scv_8 != "-": | |
if v_d == "Valor total": | |
fig_v8 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[10], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v8 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[10], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
if scv_9 != "-": | |
if v_d == "Valor total": | |
fig_v9 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[11], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v9 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[11], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
if scv_10 != "-": | |
if v_d == "Valor total": | |
fig_v10 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[12], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v10 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[12], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
if scv_11 != "-": | |
if v_d == "Valor total": | |
fig_v11 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[13], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v11 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[13], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
if scv_12 != "-": | |
if v_d == "Valor total": | |
fig_v12 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[14], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v12 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[14], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
if scv_13 != "-": | |
if v_d == "Valor total": | |
fig_v13 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[15], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v13 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[15], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
if scv_14 != "-": | |
if v_d == "Valor total": | |
fig_v14 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[16], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v14 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[16], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
if scv_15 != "-": | |
if v_d == "Valor total": | |
fig_v15 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[17], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v15 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[17], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
if scv_16 != "-": | |
if v_d == "Valor total": | |
fig_v16 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[18], df_filtrado.columns[1], df_filtrado.columns[0], "orange") | |
else: | |
fig_v16 = criar_grafico_dispersao(df_filtrado, df_filtrado.columns[18], df_filtrado.columns[2], df_filtrado.columns[0], "orange") | |
# MANIPULAÇÃO DAS COLUNAS - ESCOLHA DAS VARIÁVEIS | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 7: | |
# Utiliza o "df_filtrado" (s/ outiliers) para criação do "X" (vars indep) será utilizado na regressão linear | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Variáveis independentes | |
X = pd.DataFrame() | |
# Iterar sobre as colunas do DataFrame df_filtrado | |
for i, col in enumerate(df_filtrado.columns): | |
# Verificar se a coluna atual deve ser adicionada com base na condição e se ela existe no DataFrame | |
if (i == 3 and scv_1 != "-") or \ | |
(i == 4 and scv_2 != "-") or \ | |
(i == 5 and scv_3 != "-") or \ | |
(i == 6 and scv_4 != "-") or \ | |
(i == 7 and scv_5 != "-") or \ | |
(i == 8 and scv_6 != "-") or \ | |
(i == 9 and scv_7 != "-") or \ | |
(i == 10 and scv_8 != "-") or \ | |
(i == 11 and scv_9 != "-") or \ | |
(i == 12 and scv_10 != "-") or \ | |
(i == 13 and scv_11 != "-") or \ | |
(i == 14 and scv_12 != "-") or \ | |
(i == 15 and scv_13 != "-") or \ | |
(i == 16 and scv_14 != "-") or \ | |
(i == 17 and scv_15 != "-") or \ | |
(i == 18 and scv_16 != "-"): | |
if i < len(df_filtrado.columns): | |
X[col] = df_filtrado.iloc[:, i] | |
#X.to_excel("X.xlsx", index=False) ################################ Linha de verificação ########################### | |
n_vars = len(X.columns) | |
# REGRESSÃO LINEAR | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 8: | |
# Utiliza o "X"(vars indep) que será utilizado na regressão linear e o 'y' conforme a escolha da da (var dep) | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Variável dependente | |
if v_d == "Valor total": | |
y = df_filtrado.iloc[:, 1:2] | |
else: | |
y = df_filtrado.iloc[:, 2:3] | |
#y.to_excel("y.xlsx", index=False) ################################ Linha de verificação ########################### | |
# EXTRATREESREGRESSIOR | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 9: | |
# Inserção no código para a implementação do algorítmo de importância das variáveis | |
# -----------------------------------------------------------------------------------------------------------------# | |
scaler_x = MinMaxScaler() | |
scaler_y = MinMaxScaler() | |
input_scaler = scaler_x.fit(X) | |
output_scaler = scaler_y.fit(y) | |
x_norm = input_scaler.transform(X) | |
y_norm = output_scaler.transform(np.array(y).reshape(-1, 1)) | |
x_norm = pd.DataFrame(x_norm, columns=X.columns) | |
new_y = np.ravel(y_norm) | |
model = ExtraTreesRegressor() | |
model.fit(x_norm,new_y) | |
feat_importances = pd.Series(model.feature_importances_, index=X.columns) | |
# Converter para uma lista de tuplas | |
feat_importances_list = [(feature, round(importance * 100, 2)) for feature, importance in feat_importances.items()] | |
# Ordenar a lista em ordem decrescente de importância | |
feat_importances_list.sort(key=lambda x: x[1], reverse=True) | |
# MODELO | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 10: | |
# 1) Adicionando uma constante no X | |
# 2) Inicializando o modelo e ajustando o modelo aos dados | |
# 3) Resultados diversos | |
# 4) Equação do modelo | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Adicionando uma constante às variáveis independentes (intercepto) | |
X = sm.add_constant(X) | |
# Inicializando o modelo de regressão linear | |
modelo = sm.OLS(y, X) | |
# Ajustando o modelo aos dados | |
resultado = modelo.fit() | |
# Resultados | |
# Calculando os resíduos do modelo | |
residuos = resultado.resid | |
# Calculando Desvio Padrão dos Resíduos | |
#desvio_padrao_residuos = round(np.std(resultado.resid), 8) | |
desvio_padrao_residuos = round(np.std(residuos), 8) | |
# Calculando o erro padronizado | |
erro_padronizado = round(residuos / desvio_padrao_residuos, 5) | |
# Calculando Estatística F | |
estatistica_F = round(resultado.fvalue, 8) | |
# Obtendo Nível de Significância do Modelo | |
nivel_significancia = round(resultado.f_pvalue, 8) | |
# Calculando R² | |
r_squared = round(resultado.rsquared, 8) | |
# Calculando R² ajustado | |
r_squared_adjusted = round(resultado.rsquared_adj, 8) | |
# Obtendo Número de Observações | |
num_observacoes = int(round(resultado.nobs, 0)) | |
# Calculando Coeficiente de Correlação | |
coef_correlacao = round(np.sqrt(r_squared), 8) | |
# Comparação com a curva normal de resíduos | |
intervalos = [(-1.00, 1.00), (-1.64, 1.64), (-1.96, 1.96)] | |
# Inicializando a lista para armazenar os percentuais | |
percentuais = [] | |
# Contando o número de resíduos dentro de cada intervalo | |
for intervalo in intervalos: | |
min_intervalo, max_intervalo = intervalo | |
count = np.sum((erro_padronizado >= min_intervalo) & (erro_padronizado <= max_intervalo)) | |
percentual = round(count / len(erro_padronizado) * 100, 0) | |
percentuais.append(f"{percentual:.0f}%") | |
# Criando a string de saída | |
perc_resid = ", ".join(percentuais) | |
# Teste Kolmogorov-Smirnov (KS) | |
ks_test = sm.stats.diagnostic.kstest_normal(residuos) | |
ks_test_formatted = tuple(f"{val:.4f}" for val in ks_test) | |
# Calculando o teste de Jarque-Bera para os resíduos | |
jarque_bera_test, p_value, skewness, kurtosis = jarque_bera(residuos) | |
# Formatando os resultados com 4 casas decimais | |
jarque_bera_test = round(jarque_bera_test, 8) | |
p_value = round(p_value, 8) | |
skewness = round(skewness, 8) | |
kurtosis = round(kurtosis, 8) | |
# Extrair os coeficientes da regressão | |
coeficientes = resultado.params | |
# Calcular a distância de Cook | |
distancia_cook = resultado.get_influence().cooks_distance[0] | |
# Exibindo estatísticas do modelo | |
resultado_summary = resultado.summary() | |
resultado_html = resultado.summary().tables[1].as_html() ########################## OUTPUT ############################### | |
resultados_vars = pd.DataFrame(resultado.summary().tables[1].data[1:], columns=resultado.summary().tables[1].data[0]) | |
resultados_vars['P>|t|'] = pd.to_numeric(resultados_vars['P>|t|'], errors='coerce') | |
# ENQUADRAMENTOS NOS GRAUS DE FUNDAMENTAÇÃO | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Item 2 da tabela Item 9.2.1 da NBR 14.653-2 | |
if num_observacoes >= 6 * (n_vars + 1): | |
tab2 = "Grau III" | |
elif num_observacoes >= 4 * (n_vars + 1): | |
tab2 = "Grau II" | |
elif num_observacoes >= 3 * (n_vars + 1): | |
tab2 = "Grau I" | |
else: | |
tab2 = "Fora dos critérios" | |
# Item 5 da tabela Item 9.2.1 da NBR 14.653-2 | |
def classificar(valor): | |
if valor > 0.3: | |
return "Fora dos critérios" | |
elif valor > 0.2: | |
return "Grau I" | |
elif valor > 0.1: | |
return "Grau II" | |
else: | |
return "Grau III" | |
resultados_vars['Classificação'] = resultados_vars['P>|t|'].apply(classificar) | |
# Determinar o grau único levando em consideração todas as variáveis | |
def determinar_grau_unico(classificacoes): | |
if "Fora dos critérios" in classificacoes: | |
return "Fora dos critérios" | |
elif "Grau I" in classificacoes: | |
return "Grau I" | |
elif "Grau II" in classificacoes: | |
return "Grau II" | |
else: | |
return "Grau III" | |
tab5 = determinar_grau_unico(resultados_vars['Classificação']) | |
# Item 6 da tabela Item 9.2.1 da NBR 14.653-2 | |
if nivel_significancia <= 0.01 : | |
tab6 = "Grau III" | |
elif nivel_significancia <= 0.02 : | |
tab6 = "Grau II" | |
elif nivel_significancia <= 0.05 : | |
tab6 = "Grau I" | |
else: | |
tab6 = "Fora dos critérios" | |
# String com os resultados | |
################################### OUTPUT ########################################## | |
resultados_gerais = f""" | |
Desvio Padrão: {desvio_padrao_residuos} | |
Estatística F: {estatistica_F} / Nível de Significância Modelo: {nivel_significancia} | |
R²: {r_squared} / R² ajustado: {r_squared_adjusted} / Correlação: {coef_correlacao} | |
Número de observações: {num_observacoes} - Não utilizados: {num_outliers} | |
Número de variáveis utilizadas: {n_vars} | |
Importância Variáveis em % (ExtraTreesRegressor): {feat_importances_list} | |
------------------------------------------------------ | |
Testes de normalidade: | |
1) Comparação (curva normal) - Percentuais atingidos: {perc_resid} | |
Ideal 68% - aceitável de 64% a 75% | |
Ideal 90% - aceitável de 88% a 95% | |
Ideal 95% - aceitável de 95% a 100% | |
2) Teste de Jarque-Bera: | |
- Estatística do teste: {jarque_bera_test} | |
- Valor-p: {p_value} | |
- Assimetria (Skewness): {skewness} | |
- Curtose (Kurtosis): {kurtosis} | |
------------------------------------------------------ | |
Fundamentação - Quant. min. dados (Item 2 tab 9.2.1 NBR 14.653-2): {tab2} | |
Fundamentação - Signif. Regressores (Item 5 tab 9.2.1 NBR 14.653-2): {tab5} | |
Fundamentação - Signif. Modelo (Item 6 tab 9.2.1 NBR 14.653-2): {tab6} | |
""" | |
# Equação do modelo | |
if v_d == "Valor total": | |
equacao_modelo = df_filtrado.columns[1] + '=' | |
else: | |
equacao_modelo = df_filtrado.columns[2] + '=' | |
# Iterar sobre os coeficientes estimados | |
for nome_coluna, coeficiente in zip(X.columns, coeficientes): | |
# Se o nome da coluna for 'const', adicione apenas o coeficiente | |
if nome_coluna == 'const': | |
equacao_modelo += f" {coeficiente:.8f} +" | |
else: | |
# Adicionar o termo à equação do modelo | |
equacao_modelo += f" {coeficiente:.8f} * {nome_coluna} +" | |
# Remover o último sinal de adição | |
equacao_modelo = equacao_modelo[:-1] ################################### OUTPUT ########################################## | |
# DATAFRAME RESULTANTE DA REGRESSÃO "df_final" | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 11: | |
# 1) Concatenando o "X" e o "y" para a criação do "df_final" e na sequência acrescentando o índice do "df_filtrado" | |
# 2) Cria 'df_exporta_modelo' que será a aba no excel que servirá para salvar os parâmntros do modelo | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Adicionando a primeira coluna de df_filtrado ao início de df_final | |
ordem = df_filtrado[[df_filtrado.columns[0]]].copy() | |
df_final = pd.concat([ordem, y, X], axis=1) | |
# Dataframe que servirá para 'salvar' os parâmtros do modelo em um arqivo .xlsx | |
df_exporta_modelo = df_final.copy() | |
# Retirandso a coluna da constante do "df_final" | |
df_final = df_final.drop(columns=['const']) | |
# MATRIZ DE CORRELAÇÕES | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 12: | |
# Utilizando o "df_final" para a criação da matriz de correlações | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Calculando correlações | |
correlation_matrix = df_final.corr() | |
# Removendo a primeira coluna, assumindo que seja a primeira | |
correlation_matrix = correlation_matrix.iloc[1:, 1:] | |
# ADICIONANDO O ERRO PADRONIZADO | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 13: | |
# 1) Adicionando o erro padronizado ao "df_final" | |
# 2) Criando o 'df_maiores_que_2' com os outliers (são os dados imputados na textbox. Ver o item 1) do Comentário 5 | |
# 3) Criação da listagem que com os outliers que podem ser copiadas e coladas no textbox p/ retirar dados | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Adicionando a coluna de erro padronizado ao df_final | |
df_final['Erro Padronizado'] = erro_padronizado | |
# Criar DataFrame apenas com os dados cujo erro padronizado é maior que 2 | |
df_maiores_que_2 = df_final[abs(df_final['Erro Padronizado']) > 2] | |
df_maiores_que_2['Erro Abs'] = abs(df_maiores_que_2['Erro Padronizado']) ################### OUTPUT ################## | |
# Listagem de pontos com resíduos > 2 | |
Listagem_df_maiores_que_2 = ", ".join(map(str, df_maiores_que_2.iloc[:, 0].tolist())) ############ OUTPUT ############ | |
# VALORES AJUSTADOS X PREÇOS OBSERVADOS | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 14: | |
# 1) Calculando os valores de 'X'. Ver o item 1) do comentário 10 | |
# 2) Adicionando estes valores ao 'df_final' | |
# 3) A partir do 'df_final' é criado o 'df_correl' somente com as colunas 'Observados' e 'Calculados' | |
# 4) Criação de uma cópia do 'df_correl', antes de desfazer a conversão das escalas, para plotagem de um gráfico | |
# 5) Desfazendo a conversão das escalas para concatenar ao 'df_final' | |
# 6) Criando a coluna 'Diferença %' no 'df_correl' | |
# 7) Faznedo o merge do 'df_final' e do 'df_correl' | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Obtendo os valores previstos | |
# Dados | |
valores_previstos = resultado.predict(X) | |
# Adicionando os valores previstos como uma nova coluna ao df_final | |
df_final['Valores Ajustados'] = round(valores_previstos, 8) | |
# Criando uma dataframe para os Valores Ajustados x Preços Observados | |
if v_d == "Valor total": | |
df_correl = df_final[[df_filtrado.columns[0], df_filtrado.columns[1], 'Valores Ajustados']] | |
df_correl = df_correl.rename(columns={df_filtrado.columns[1]: 'Observados'}) | |
df_correl = df_correl.rename(columns={'Valores Ajustados': 'Calculados'}) | |
else: | |
df_correl = df_final[[df_filtrado.columns[0], df_filtrado.columns[2], 'Valores Ajustados']] | |
df_correl = df_correl.rename(columns={df_filtrado.columns[2]: 'Observados'}) | |
df_correl = df_correl.rename(columns={'Valores Ajustados': 'Calculados'}) | |
# Criação de uma cópia do 'df_correl' | |
df_correl_grafico = df_correl.copy() | |
# Desfazendo a conversão da escala | |
if scv_d == 'lny': | |
df_correl['Calculados'] = round(np.exp(df_correl['Calculados']), 8) | |
df_correl['Observados'] = round(np.exp(df_correl['Observados']), 8) | |
elif scv_d == '1/y': | |
df_correl['Calculados'] = round(1 / df_correl['Calculados'], 8) | |
df_correl['Observados'] = round(1 / df_correl['Observados'], 8) | |
elif scv_d == 'y²': | |
df_correl['Calculados'] = round(np.sqrt(df_correl['Calculados']), 8) | |
df_correl['Observados'] = round(np.sqrt(df_correl['Observados']), 8) | |
else: | |
pass # Nenhuma transformação é necessária | |
# Criando uma coluna de diferença percentual | |
################################### OUTPUT ########################################## | |
df_correl['Diferença %'] = round(((df_correl['Calculados']/df_correl['Observados'])-1)*100, 8) | |
# Usando a primeira coluna de cada DataFrame como chave para o merge | |
################################### OUTPUT ########################################## | |
df_final_2 = pd.merge(df_final, df_correl, left_on=df_final.columns[0], right_on=df_correl.columns[0], how='left') | |
# ARQUIVO EXCEL | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 15: | |
# 1) Cria um output de planilha do excel vazio e: | |
# 2) Acrescenta 'df_original': planilha original de dados (todas as variáveis, sem conversão de escala e todos os dados) | |
# 3) Acrescenta 'df_dados_utilizados': somente as variáveis e os dados utilizado (sem conversão de escala) | |
# 4) Acrescenta 'df_outliers': dados retidados do modelo | |
# 5) Acrescenta 'df_correl': Obs x Calc | |
# 6) Cria um aba no arquivo com o nome 'Resultados' e acrescenta todos os resultados estatísticos | |
# 7) Acrescenta o 'df_exporta_modelo' com o nome 'Model'. Ver item 2) do Comentáro 11. Serve p/ carregar modelo futuramente | |
# 8) Cria uma aba chamada 'avaliando' que serve de modelo para quando este modelo cfora carregado novamente | |
# -----------------------------------------------------------------------------------------------------------------# | |
current_date = datetime.now().strftime("%d%b%y").lower() | |
output_file = 'modelo.xlsx' ################################### OUTPUT ########################################## | |
output_file = f"{name_model}_model_{current_date}.xlsx" | |
with pd.ExcelWriter(output_file, engine='xlsxwriter') as writer: | |
# Salve o DataFrame 'DADOS INICIAIS' na planilha | |
df_original.to_excel(writer, sheet_name='Dados Originais', index=False) | |
# Salve o DataFrame 'DADOS UTILIZADOS' na planilha | |
df_dados_utilizados.to_excel(writer, sheet_name='Dados Utilizados', index=False) | |
# Salve o DataFrame 'DADOS NÃO UTILIZADOS' na planilha | |
df_outliers.to_excel(writer, sheet_name='Dados Não utilizados', index=False) | |
# Salve o DataFrame 'MÁXIMOS E MÍNIMOS' na planilha | |
df_limites_var_final.to_excel(writer, sheet_name='Fronteiras', index=False) | |
# Salve o DataFrame 'PLANILHA OBS X CALC' na planilha | |
df_correl.to_excel(writer, sheet_name='Obs x Calc', index=False) | |
# String com os resultados | |
resultados = pd.DataFrame({ | |
'Desvio Padrão': [desvio_padrao_residuos], | |
'Estatística F': [estatistica_F], | |
'Nível de Significância do Modelo': [nivel_significancia], | |
'R²': [r_squared], | |
'R² ajustado': [r_squared_adjusted], | |
'Correlação': [coef_correlacao], | |
'Número de observações': [num_observacoes], | |
'Número de dados não utilizados': [num_outliers], | |
'Número de variáveis utilizadas': [n_vars], | |
'1) Comparação (curva normal 68% 90% 95%)': [perc_resid], | |
'2) Estatística do teste': [jarque_bera_test], | |
'- Valor-p': [p_value], | |
'- Assimetria (Skewness)': [skewness], | |
'- Curtose (Kurtosis)': [kurtosis], | |
'Fundamentação - Quant. min. dados (Item 2 tab 9.2.1 NBR 14.653-2)': [tab2], | |
'Fundamentação - Signif. Regressores (Item 5 tab 9.2.1 NBR 14.653-2)': [tab5], | |
'Fundamentação - Signif. Modelo (Item 6 tab 9.2.1 NBR 14.653-2)': [tab6] | |
}) | |
# Transponha o DataFrame | |
resultados = resultados.T.reset_index() | |
# Defina os nomes das colunas do novo DataFrame | |
resultados.columns = ['Resultado', 'Valor'] | |
#resultados.to_excel(writer, sheet_name='Result_gerais', index=False) | |
# Salve o DataFrame 'RESULTADOS VARS' na planilha | |
#resultados_vars.to_excel(writer, sheet_name='Result_vars', index=False) | |
# Combine 'Result_gerais' e 'Result_vars' na aba 'Resultados_estatísticos' | |
# Adicione uma coluna vazia entre os DataFrames | |
resultados_vars_shifted = pd.concat([pd.DataFrame(columns=['', '']), resultados_vars], axis=1) | |
# Concatenar os dois DataFrames lado a lado | |
resultados_estatisticos = pd.concat([resultados, resultados_vars_shifted], axis=1) | |
# Escrever o DataFrame combinado na aba 'Resultados_estatísticos' | |
resultados_estatisticos.to_excel(writer, sheet_name='Resultados_estatísticos', index=False) | |
# Salve o DataFrame 'DADOS PARA REGRESSÃO' na planilha | |
#df_exporta_modelo.to_excel(writer, sheet_name='Model', index=False) | |
# Salve o DataFrame 'PLANILHA MODELO PARA AVALIAÇÃO' na planilha 'relatório' | |
df_avalia_copy = df_avalia.copy() | |
df_avalia_copy = df_avalia_copy.iloc[0:0] | |
df_avalia_copy.to_excel(writer, sheet_name='avaliando', index=False) | |
# Acrescente o DataFrame 'df_scv' (svc e escalas) na aba 'Escalas' | |
df_scv.to_excel(writer, sheet_name='Escalas', index=False) | |
# PONTOS INFLUENCIANTES | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 16: | |
# 1) Por meio da distância de cook, calcula-se os pontos influeniantes | |
# -----------------------------------------------------------------------------------------------------------------# | |
limite_cook = 1 | |
pontos_influentes = [] | |
for i, cook_dist in enumerate(distancia_cook): | |
if cook_dist > limite_cook: | |
pontos_influentes.append(df_final.iloc[i, 0]) # Usando a primeira coluna como rótulo | |
# Transformando a lista em uma string separada por vírgula | |
string_pontos_influentes = ", ".join(map(str, pontos_influentes)) ##################### OUTPUT ##################### | |
# GRÁFICOS | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 17: | |
# 1) Gráfico de resíduos padronizados | |
# 2) Histograma de resíduos | |
# 3) Pontos influenciantes | |
# 4) Gráfico de Valores ajustados x Preços observados | |
# 5) Gráfico do ExtraTreesRegessor - influência das variáveis. Ver Comentário 9 | |
# 6) Matriz de correlações | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Gráfico dos resíduos padronizados | |
fig, ax1 = plt.subplots(figsize=(8, 4)) | |
ax1.scatter(df_final['Valores Ajustados'], erro_padronizado, color='orange', alpha=0.6) | |
ax1.axhline(y=0, color='black', linestyle='--', linewidth=1) # Linha zero | |
ax1.axhline(y=2, color='red', linestyle='-', linewidth=1) # Linhas vermelhas em ±2 | |
ax1.axhline(y=-2, color='red', linestyle='-', linewidth=1) | |
ax1.set_title('Gráfico de Resíduos Padronizados') | |
ax1.set_xlabel('Valores Ajustados') | |
ax1.set_ylabel('Resíduos Padronizados') | |
ax1.grid(True) | |
for i, txt in enumerate(df_final.iloc[:, 0]): | |
if abs(erro_padronizado[i]) > 2: | |
ax1.annotate(txt, (df_final['Valores Ajustados'][i], erro_padronizado[i]), xytext=(5, 5), | |
textcoords='offset points', fontsize=12, color='darkred') | |
fig.savefig('residuos_padronizados.png') | |
plt.close(fig) # Fecha a figura para que o próximo gráfico seja independente | |
# Histograma dos resíduos padronizados | |
fig, ax2 = plt.subplots(figsize=(8, 4)) | |
sns.histplot(erro_padronizado, kde=True, color='orange', alpha=0.6, ax=ax2) | |
ax2.set_title('Histograma dos Resíduos Padronizados') | |
ax2.set_xlabel('Resíduos Padronizados') | |
ax2.set_ylabel('Frequência') | |
ax2.grid(True) | |
fig.savefig('histograma_residuos_padronizados.png') | |
plt.close(fig) | |
# Gráfico da distância de Cook | |
fig, ax3 = plt.subplots(figsize=(8, 4)) | |
ax3.plot(distancia_cook, marker='o', linestyle='None', color='orange') | |
ax3.axhline(y=1, color='red', linestyle='--', linewidth=1) | |
ax3.set_title('Gráfico da Distância de Cook') | |
ax3.set_xlabel('Número da Observação') | |
ax3.set_ylabel('Distância de Cook') | |
ax3.grid(True) | |
for i, valor in enumerate(distancia_cook): | |
if valor > 1: | |
ax3.annotate(str(i), (i, valor), xytext=(5, 5), textcoords='offset points', fontsize=12, color='darkred') | |
fig.savefig('distancia_cook.png') | |
plt.close(fig) | |
# Gráfico Valores Ajustados vs Preços Observados | |
fig, ax4 = plt.subplots(figsize=(8, 4)) | |
x_values = df_correl_grafico['Observados'] | |
y_values = df_correl_grafico['Calculados'] | |
slope, intercept = np.polyfit(x_values, y_values, 1) | |
ax4.scatter(x_values, y_values, color='black') | |
ax4.plot(x_values, slope * x_values + intercept, color='orange', linestyle='--', linewidth=2) | |
ax4.set_title('Valores Ajustados vs Preços Observados') | |
ax4.set_xlabel('Preços Observados') | |
ax4.set_ylabel('Valores Ajustados') | |
ax4.grid(True) | |
fig.savefig('valores_ajustados_vs_observados.png') | |
plt.close(fig) | |
# Matriz de correlações | |
fig, ax6 = plt.subplots(figsize=(8, 4)) | |
ax6.set_title('Matriz de Correlação') | |
palette = sns.light_palette("orange", as_cmap=True) | |
sns.heatmap(correlation_matrix, annot=True, cmap=palette, linewidths=0.3, ax=ax6, annot_kws={"size": 6}, | |
cbar_kws={"shrink": 0.8}) | |
fig.savefig('matriz_correlacao.png') | |
plt.close(fig) | |
################################### OUTPUT ########################################## | |
# AVALIAÇÃO | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 18: | |
# 1) No momento de gerar modelo é possível, por meio da aba "avaliando" da planilha imputada, fazer uma avalaição | |
# 2) Criadas duas cópias do "df_aval". | |
# -----------------------------------------------------------------------------------------------------------------# | |
try: | |
# Carregando o(s) avaliando(s) | |
df_aval = pd.read_excel(planilha.name, 'avaliando') | |
# avaliando(s) | |
df_aval_final = df_aval.copy() | |
df_aval_original = pd.DataFrame() | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 19: | |
# 1) O 'df_aval_final' serve como agregador das informações, mantendo a forma original para posterior apresentação | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Para criar um dataframe final sem as escalas convertidas e apenas com as variáveis escolhidas | |
for i, col in enumerate(df_aval_final.columns): | |
# Verificar se a coluna atual deve ser adicionada com base na condição e se ela existe no DataFrame | |
if (i == 0 and scv_1 != "-") or \ | |
(i == 1 and scv_2 != "-") or \ | |
(i == 2 and scv_3 != "-") or \ | |
(i == 3 and scv_4 != "-") or \ | |
(i == 4 and scv_5 != "-") or \ | |
(i == 5 and scv_6 != "-") or \ | |
(i == 6 and scv_7 != "-") or \ | |
(i == 7 and scv_8 != "-") or \ | |
(i == 8 and scv_9 != "-") or \ | |
(i == 9 and scv_10 != "-") or \ | |
(i == 10 and scv_11 != "-") or \ | |
(i == 11 and scv_12 != "-") or \ | |
(i == 12 and scv_13 != "-") or \ | |
(i == 13 and scv_14 != "-") or \ | |
(i == 14 and scv_15 != "-") or \ | |
(i == 15 and scv_16 != "-"): | |
if i < len(df_aval_final.columns): | |
df_aval_original[col] = df_aval_final.iloc[:, i] | |
#df_aval_original.to_excel("df_aval_original.xlsx") ##################### Linha de verificação ################## | |
#df_var_ext = calc_extrapola(df_aval_original, df_limites_var) ############# Linha de verificação ############### | |
# VERIFICAÇÃO DA EXTRAPOLAÇÃO DSA VARIÁVEIS | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 20: | |
# 1) A partir do 'df_aval_original' cria-se a coluna "extrapola" pela função 'calc_extrapola' | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Aplicação da função para criação de coluna com estrapolação das variáveis | |
calc_extrapola(df_aval_original, df_limites_var_final) | |
# DATAFRAME PARA IMPUTAR NO MODELO | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 21: | |
# 1) A partir do 'df_aval' faz-se a conversão das escalas | |
# 2) Criação do 'X_aval' (variáveis independentes dos dados) | |
# 3) Agregando os valores previstos no 'df_aval_original' | |
# 4) Cálculo do Campo de Arbítrio e Intervalo de Confiança de 80%, agregando as colunas ao 'df_aval_original' | |
# 5) Cálculo da 'Precisão' e criação de coluna no 'df_aval_original' | |
# -----------------------------------------------------------------------------------------------------------------# | |
if model == "Carregar": | |
# Carrega o arquivo Excel da planilha fornecida (ignorando o cabeçalho na primeira linha) | |
df_escalas = pd.read_excel(planilha.name, sheet_name="Escalas") | |
# Preenchendo as variáveis com base nos valores da planilha, ajustando para o cabeçalho | |
v_d = df_escalas.iloc[0, 2] | |
scv_d = df_escalas.iloc[0, 1] | |
scv_1 = df_escalas.iloc[1, 1] | |
scv_2 = df_escalas.iloc[2, 1] | |
scv_3 = df_escalas.iloc[3, 1] | |
scv_4 = df_escalas.iloc[4, 1] | |
scv_5 = df_escalas.iloc[5, 1] | |
scv_6 = df_escalas.iloc[6, 1] | |
scv_7 = df_escalas.iloc[7, 1] | |
scv_8 = df_escalas.iloc[8, 1] | |
scv_9 = df_escalas.iloc[9, 1] | |
scv_10 = df_escalas.iloc[10, 1] | |
scv_11 = df_escalas.iloc[11, 1] | |
scv_12 = df_escalas.iloc[12, 1] | |
scv_13 = df_escalas.iloc[13, 1] | |
scv_14 = df_escalas.iloc[14, 1] | |
scv_15 = df_escalas.iloc[15, 1] | |
scv_16 = df_escalas.iloc[16, 1] | |
# alterar escalas (para rodar o modelo) | |
aplicar_operacao(df_aval, scv_1, 0) | |
aplicar_operacao(df_aval, scv_2, 1) | |
aplicar_operacao(df_aval, scv_3, 2) | |
aplicar_operacao(df_aval, scv_4, 3) | |
aplicar_operacao(df_aval, scv_5, 4) | |
aplicar_operacao(df_aval, scv_6, 5) | |
aplicar_operacao(df_aval, scv_7, 6) | |
aplicar_operacao(df_aval, scv_8, 7) | |
aplicar_operacao(df_aval, scv_9, 8) | |
aplicar_operacao(df_aval, scv_10, 9) | |
aplicar_operacao(df_aval, scv_11, 10) | |
aplicar_operacao(df_aval, scv_12, 11) | |
aplicar_operacao(df_aval, scv_13, 12) | |
aplicar_operacao(df_aval, scv_14, 13) | |
aplicar_operacao(df_aval, scv_15, 14) | |
aplicar_operacao(df_aval, scv_16, 15) | |
# Criando um dataframe apenas com as variáveis escolhidas e com as escalas convertidas. | |
X_aval = pd.DataFrame() | |
# Iterar sobre as colunas do DataFrame para fazer a predição de valor | |
for i, col in enumerate(df_aval.columns): | |
# Verificar se a coluna atual deve ser adicionada com base na condição e se ela existe no DataFrame | |
if (i == 0 and scv_1 != "-") or \ | |
(i == 1 and scv_2 != "-") or \ | |
(i == 2 and scv_3 != "-") or \ | |
(i == 3 and scv_4 != "-") or \ | |
(i == 4 and scv_5 != "-") or \ | |
(i == 5 and scv_6 != "-") or \ | |
(i == 6 and scv_7 != "-") or \ | |
(i == 7 and scv_8 != "-") or \ | |
(i == 8 and scv_9 != "-") or \ | |
(i == 9 and scv_10 != "-") or \ | |
(i == 10 and scv_11 != "-") or \ | |
(i == 11 and scv_12 != "-") or \ | |
(i == 12 and scv_13 != "-") or \ | |
(i == 13 and scv_14 != "-") or \ | |
(i == 14 and scv_15 != "-") or \ | |
(i == 15 and scv_16 != "-"): | |
if i < len(df_aval.columns): | |
X_aval[col] = df_aval.iloc[:, i] | |
# Adicionando a constante | |
X_aval.insert(0, 'const', 1) ############################# Linha de verificação ############################### | |
# Avaliando(s) no modelo para predição de valor | |
valores_previstos_aval = resultado.predict(X_aval) | |
df_aval_original['VALOR'] = round(valores_previstos_aval, 8) | |
# Desfazendo a conversão das escalas | |
if scv_d == 'lny': | |
df_aval_original['VALOR'] = round(np.exp(df_aval_original['VALOR']), 8) | |
elif scv_d == '1/y': | |
df_aval_original['VALOR'] = round(1 / df_aval_original['VALOR'], 8) | |
elif scv_d == 'y²': | |
df_aval_original['VALOR'] = round(np.sqrt(df_aval_original['VALOR']), 8) | |
else: | |
pass # Nenhuma transformação é necessária | |
# Campo de arbítrio | |
df_aval_original['LI_CA'] = round((df_aval_original['VALOR']*0.85), 2) | |
df_aval_original['LS_CA'] = round((df_aval_original['VALOR']*1.15), 2) | |
# Intervalo de Confiança de 80% | |
# Calcular os intervalos de confiança para a média prevista | |
intervalo_confianca = resultado.get_prediction(X_aval).summary_frame(alpha=0.2) | |
# Extrair os limites inferior e superior do intervalo de confiança | |
limite_inferior = intervalo_confianca['mean_ci_lower'] | |
limite_superior = intervalo_confianca['mean_ci_upper'] | |
# Adicionar as colunas ao DataFrame df_aval_original | |
df_aval_original['LI_IC'] = limite_inferior.values | |
df_aval_original['LS_IC'] = limite_superior.values | |
if scv_d == 'lny': | |
df_aval_original['LI_IC'] = round(np.exp(df_aval_original['LI_IC']), 2) | |
df_aval_original['LS_IC'] = round(np.exp(df_aval_original['LS_IC']), 2) | |
elif scv_d == '1/y': | |
df_aval_original['LI_IC'] = round(1 / df_aval_original['LI_IC'], 2) | |
df_aval_original['LS_IC'] = round(1 / df_aval_original['LS_IC'], 2) | |
elif scv_d == 'y²': | |
df_aval_original['LI_IC'] = round(np.sqrt(df_aval_original['LI_IC']), 2) | |
df_aval_original['LS_IC'] = round(np.sqrt(df_aval_original['LS_IC']), 2) | |
else: | |
pass # Nenhuma transformação é necessária | |
df_aval_original['LI_IC_%'] = round(((df_aval_original['VALOR']-df_aval_original['LI_IC'])/df_aval_original['VALOR'])*100, 2) | |
df_aval_original['LS_IC_%'] = round(((df_aval_original['LS_IC']-df_aval_original['VALOR'])/df_aval_original['VALOR'])*100, 2) | |
df_aval_original['TOTAL_IC_%'] = round(df_aval_original['LI_IC_%'] + df_aval_original['LS_IC_%'], 2) | |
# Aplicação das condições para determinar 'PRECISÃO' | |
df_aval_original['PRECISÃO'] = "" # Inicializa a coluna 'PRECISÃO' | |
df_aval_original.loc[df_aval_original['TOTAL_IC_%'] <= 30, 'PRECISÃO'] = "Grau III" | |
df_aval_original.loc[(df_aval_original['TOTAL_IC_%'] > 30) & (df_aval_original['TOTAL_IC_%'] <= 40), 'PRECISÃO'] = "Grau II" | |
df_aval_original.loc[(df_aval_original['TOTAL_IC_%'] > 40) & (df_aval_original['TOTAL_IC_%'] <= 50), 'PRECISÃO'] = "Grau I" | |
df_aval_original.loc[df_aval_original['TOTAL_IC_%'] > 50, 'PRECISÃO'] = "Fora dos critérios" | |
# Criação de um índice para os avaliandos | |
df_aval_original.insert(0, 'nº_aval', range(1, len(df_aval_original) + 1)) | |
# DATA FRAME COM AS EXTRAPOLAÇÕES | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 22: | |
# 1) Cria o 'df_resultado' a partir do uma cópia do 'df_aval_original' | |
# 2) A partir do uma cópia do 'df_resultado', cria-se o 'X_ext' (na fronteira), para aplicação no modelo | |
# 3) Reisere-se os valor previstos (convertendos as escalas) em uma coluna do 'df_resultado' | |
# 4) Reisere-se os valor previstos (convertendos as escalas) na coluna 'VALOR_ext' do 'df_aval_original' | |
# -----------------------------------------------------------------------------------------------------------------# | |
#if not df_aval_original.empty: | |
# Copiar o DataFrame original | |
df_resultado = df_aval_original.copy() | |
# Filtrar os dados onde 'extrapola' não é 'sem extrapolação' | |
df_resultado = df_resultado[df_resultado['extrapola'] != 'sem extrapolação'] | |
# Separar a coluna 'nº_aval' antes de fazer qualquer seleção de colunas | |
numeracao = df_resultado['nº_aval'] | |
# Excluir a coluna 'nº_aval' temporariamente para o processamento | |
df_resultado = df_resultado.drop(columns=['nº_aval']) | |
# Encontre o índice da coluna 'extrapola' | |
indice_extrapola = df_resultado.columns.get_loc('extrapola') | |
# Selecione todas as colunas até a coluna 'extrapola' | |
df_resultado = df_resultado.iloc[:, :indice_extrapola] | |
# Loop para ajustar os valores conforme os limites | |
for index, row in df_resultado.iterrows(): | |
for col in df_resultado.columns: | |
valor = row[col] | |
limite_min = df_limites_var_final.iloc[0][col] | |
limite_max = df_limites_var_final.iloc[1][col] | |
# Substituir se o valor for menor que o limite mínimo | |
if valor < limite_min: | |
df_resultado.at[index, col] = limite_min | |
# Substituir se o valor for maior que o limite máximo | |
elif valor > limite_max: | |
df_resultado.at[index, col] = limite_max | |
# Reinsere a coluna 'nº_aval' no DataFrame | |
df_resultado['nº_aval'] = numeracao.values | |
# Reorganiza as colunas para garantir que 'nº_aval' seja a primeira | |
cols = ['nº_aval'] + [col for col in df_resultado.columns if col != 'nº_aval'] | |
df_resultado = df_resultado[cols] | |
# Exibir o resultado final | |
X_ext = df_resultado.copy() | |
X_ext = X_ext.iloc[:, 1:] | |
# alterar escalas (para rodar o modelo) | |
aplicar_operacao(X_ext, scv_1, 0) | |
aplicar_operacao(X_ext, scv_2, 1) | |
aplicar_operacao(X_ext, scv_3, 2) | |
aplicar_operacao(X_ext, scv_4, 3) | |
aplicar_operacao(X_ext, scv_5, 4) | |
aplicar_operacao(X_ext, scv_6, 5) | |
aplicar_operacao(X_ext, scv_7, 6) | |
aplicar_operacao(X_ext, scv_8, 7) | |
aplicar_operacao(X_ext, scv_9, 8) | |
aplicar_operacao(X_ext, scv_10, 9) | |
aplicar_operacao(X_ext, scv_11, 10) | |
aplicar_operacao(X_ext, scv_12, 11) | |
aplicar_operacao(X_ext, scv_13, 12) | |
aplicar_operacao(X_ext, scv_14, 13) | |
aplicar_operacao(X_ext, scv_15, 14) | |
aplicar_operacao(X_ext, scv_16, 15) | |
X_ext.insert(0, 'const', 1) ############################### Linha de verificação ################################ | |
# Avaliando(s) | |
valores_previstos_ext = resultado.predict(X_ext) | |
df_resultado['VALOR'] = round(valores_previstos_ext, 8) | |
if scv_d == 'lny': | |
df_resultado['VALOR'] = round(np.exp(df_resultado['VALOR']), 8) | |
elif scv_d == '1/y': | |
df_resultado['VALOR'] = round(1 / df_resultado['VALOR'], 8) | |
elif scv_d == 'y²': | |
df_resultado['VALOR'] = round(np.sqrt(df_resultado['VALOR']), 8) | |
else: | |
pass # Nenhuma transformação é necessária | |
df_resultado ################################ Linha de verificação ################################ | |
df_aval_original['VALOR_fronteira'] = round(valores_previstos_ext, 8) | |
if scv_d == 'lny': | |
df_aval_original['VALOR_fronteira'] = round(np.exp(df_aval_original['VALOR_fronteira']), 8) | |
elif scv_d == '1/y': | |
df_aval_original['VALOR_fronteira'] = round(1 / df_aval_original['VALOR_fronteira'], 8) | |
elif scv_d == 'y²': | |
df_aval_original['VALOR_fronteira'] = round(np.sqrt(df_aval_original['VALOR_fronteira']), 8) | |
else: | |
pass # Nenhuma transformação é necessária | |
# Salve o DataFrame 'result' em uma planilha | |
df_aval_original.to_excel("planilha_aval.xlsx", index=True) ####################### OUTPUT ####################### | |
except: | |
# Se a aba não existir, crie um DataFrame vazio | |
df_aval_original = pd.DataFrame() | |
# Salve o DataFrame em uma planilha | |
df_aval_original.to_excel("planilha_aval.xlsx", index=True) | |
# LAUDO | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 27: | |
# 1) Cria as strings patra as seções do laudo | |
# 2) Gera documento em word | |
# -----------------------------------------------------------------------------------------------------------------# | |
# criação de strings para os relatórios da interface e do word | |
trabalho = f""" | |
Identificação do trabalho técnico: {laudo} | |
Data de referência do laudo: {data_ref} | |
Data de elaboração do laudo: {data_laudo} | |
""" | |
dados_resp = f""" | |
Responsável Técnico: {nome} | |
Profissão: {prof} | |
Entidade de Classe: {ent} {uf} | |
Número do registro: {reg} | |
""" | |
##### | |
introd = f""" | |
Logradouro e número: {lograd} | |
Município: {munic} | |
Tipo de imóvel: {tipo_imo} | |
Solicitante: {solic} | |
Finalidade: {finalidade} | |
Objetivo: {objetivo} | |
Pressupostos, Ressalvas e Fatores Limitantes: {press} | |
""" | |
##### | |
regiao = f""" | |
Infraestrutura: {str(infra).replace("[", "").replace("]", "").replace("'", "")} | |
Serviços públicos: {str(serv).replace("[", "").replace("]", "").replace("'", "")} | |
Uso: {uso} | |
Padrão predominante na região: {pad_reg} | |
Tipo de via de acesso: {tipo_via} | |
Outras observações: {obs_gerais} | |
""" | |
##### | |
diag = f""" | |
Performance: {per} | |
Nível de Ofertas do Segmento: {ofe} | |
Liquidez: {liq} | |
Outras informações: {dia} | |
""" | |
metodologia = f""" | |
Para a verificação do valor locativo mensal, foi utilizado o Método Comparativo de Dados de Mercado, conforme preconiza a NBR 14653-2:2011, Norma Brasileira de Avaliação de Bens- Imóveis Urbanos. Definido como aquele pelo qual o valor de um bem é determinado por comparação com outros de características semelhantes, através de tratamento técnico dos atributos dos elementos comparáveis, constituintes da amostra utilizada. | |
Os elementos amostrais tomados como referência, embora comparáveis ao imóvel avaliando, possuem características distintas devido à típica heterogeneidade do produto oferecido pelo mercado de imóveis. Torna-se imprescindível, então, a homogeneização dos dados amostrais. Entende-se por homogeneização o tratamento dispensado aos dados objetivando retirar as discrepâncias existentes entre as características de cada imóvel tomado como referência as do imóvel avaliando. A fim de que se alcance um grau maior de precisão nos trabalhos avaliatórios a NBR 14653-2:2011, Norma Brasileira de Avaliação de Bens - Imóveis Urbanos, recomenda que a homogeneização deve ser baseada em processos de inferência estatística, ao invés de utilizar fatores determinísticos e ponderações de ordem subjetiva, que implicam em uma sensível perda do nível de precisão dos trabalhos avaliatórios. | |
O mercado imobiliário não se vincula diretamente a índices econômicos e não segue um mesmo padrão em toda a cidade. Sendo assim, o comportamento das variáveis explicativas do valor apresenta oscilações diferenciadas em regiões distintas e em determinados intervalos de tempo, as quais podem contribuir de forma variada no preço final dos imóveis, de acordo com suas peculiaridades. Portanto, empregou-se a regressão múltipla para a homogeneização dos dados. Esta é a técnica adequada quando se deseja estudar o comportamento de uma variável, dita dependente, em relação a outras variáveis, ditas independentes, que são responsáveis por sua formação. | |
""" | |
##### | |
assinatura = f""" | |
Data: {data_laudo} | |
{nome} | {prof} | |
{ent}-{uf} {reg} | |
""" | |
# Gerando documento em word | |
doc = Document() | |
doc.add_heading('Relatório de Avaliação de Imóvel', level=1) | |
sections = [ | |
(trabalho, "Trabalho Técnico"), | |
(dados_resp, "Informações do Responsável Técnico"), | |
(introd, "Introdução"), | |
(regiao, "Características da Região"), | |
(diag, "Diagnóstico de Mercado"), | |
(metodologia, "Metodologia"), | |
(resultados_gerais, "Resultados Gerais Modelo"), | |
("", "Análise Gráfica"), | |
(assinatura, ""), | |
] | |
for content, title in sections: | |
doc.add_heading(title, level=2) | |
if title == "Resultados Gerais do Modelo": | |
# Adiciona a tabela do DataFrame | |
table = doc.add_table(rows=1, cols=len(resultados_gerais.columns)) | |
hdr_cells = table.rows[0].cells | |
for i, column_name in enumerate(resultados_gerais.columns): | |
paragraph = hdr_cells[i].paragraphs[0] | |
run = paragraph.runs[0] if paragraph.runs else paragraph.add_run() | |
run.text = str(column_name) | |
run.font.size = Pt(12) # Tamanho da fonte para o cabeçalho da tabela | |
for index, row in resultados_gerais.iterrows(): | |
row_cells = table.add_row().cells | |
for i, value in enumerate(row): | |
paragraph = row_cells[i].paragraphs[0] | |
run = paragraph.runs[0] if paragraph.runs else paragraph.add_run() | |
run.text = str(value) | |
run.font.size = Pt(10) # Define o tamanho da fonte para 8 para os dados da tabela | |
elif title == "Análise Gráfica": | |
# Adiciona os gráficos ao documento | |
doc.add_picture('residuos_padronizados.png', width=Inches(6)) | |
doc.add_picture('histograma_residuos_padronizados.png', width=Inches(6)) | |
doc.add_picture('distancia_cook.png', width=Inches(6)) | |
doc.add_picture('valores_ajustados_vs_observados.png', width=Inches(6)) | |
doc.add_picture('matriz_correlacao.png', width=Inches(6)) | |
else: | |
p = doc.add_paragraph() | |
run = p.add_run(content) | |
run.font.size = Pt(12) | |
if title == "": # Seção de assinatura | |
p.alignment = WD_PARAGRAPH_ALIGNMENT.RIGHT | |
else: | |
p.alignment = WD_PARAGRAPH_ALIGNMENT.LEFT | |
# Adicionando a seção com os dados utilizados como tabela | |
doc.add_heading("Dados Utilizados", level=2) | |
# Cria uma tabela no Word com o DataFrame df_dados_utilizados | |
table = doc.add_table(rows=1, cols=len(df_dados_utilizados.columns)) | |
hdr_cells = table.rows[0].cells | |
# Preenche as colunas da tabela | |
for i, column_name in enumerate(df_dados_utilizados.columns): | |
hdr_cells[i].text = str(column_name) | |
# Ajustando a fonte do cabeçalho | |
paragraph = hdr_cells[i].paragraphs[0] | |
run = paragraph.runs[0] | |
run.font.size = Pt(5) # Define o tamanho da fonte como 5 | |
# Preenche as linhas da tabela | |
for index, row in df_dados_utilizados.iterrows(): | |
row_cells = table.add_row().cells | |
for i, value in enumerate(row): | |
row_cells[i].text = str(value) | |
# Ajustando a fonte das células de dados | |
paragraph = row_cells[i].paragraphs[0] | |
run = paragraph.runs[0] | |
run.font.size = Pt(5) # Define o tamanho da fonte como 5 | |
# Salva o documento | |
doc.save('relatorio_avaliacao.doc') | |
# OUTPUTS | |
# -----------------------------------------------------------------------------------------------------------------# | |
# Comentário 23: | |
# 1) Ao lado de cada output consta a linha do código | |
# -----------------------------------------------------------------------------------------------------------------# | |
return ( | |
#df_original, | |
string_colunas, | |
resultados_gerais, | |
equacao_modelo, | |
resultados_vars, | |
df_final_2, | |
Listagem_df_maiores_que_2, | |
string_pontos_influentes, | |
df_maiores_que_2, | |
df_outliers, | |
df_limites_var_final, | |
'residuos_padronizados.png', | |
'histograma_residuos_padronizados.png', | |
'distancia_cook.png', | |
'valores_ajustados_vs_observados.png', | |
'matriz_correlacao.png', | |
df_aval_original, | |
'planilha_aval.xlsx', | |
output_file, | |
fig_v1, | |
fig_v2, | |
fig_v3, | |
fig_v4, | |
fig_v5, | |
fig_v6, | |
fig_v7, | |
fig_v8, | |
fig_v9, | |
fig_v10, | |
fig_v11, | |
fig_v12, | |
fig_v13, | |
fig_v14, | |
fig_v15, | |
fig_v16, | |
trabalho, | |
dados_resp, | |
introd, | |
regiao, | |
diag, | |
metodologia, | |
'relatorio_avaliacao.doc' | |
) | |
# -------------------------------------- # | |
lista_finalidades = ["-", | |
"ADJUDICAÇÃO COMPULSÓRIA", "ALUGUEL", "AQUISIÇÃO", "CAUÇÃO", "CEDÊNCIA", "DAÇÃO EM PAGAMENTO", | |
"DEC_PROJ DE LEI", "DECLARATÓRIA", "DESAPROPRIAÇÃO PARCIAL", "DESAPROPRIAÇÃO TOTAL", "DOAÇÃO", | |
"EMBARGOS À ARREMATAÇÃO", "EMBARGOS A EXECUÇÃO FISCAL", "EQUIVALÊNCIA", "EXECUÇÃO FISCAL", | |
"FUTURA LICITAÇÃO", "GARANTIA", "INDENIZAÇÃO", "IPTU", "MULTA IMÓVEL INVENTARIADO", "PERMUTA", | |
"PROJETO ESPECIAL", "PRÓPRIO MUNICIPAL", "PRÓPRIO MUNICIPAL - ALIENAÇÃO", | |
"PRÓPRIO MUNICIPAL - CONCESSÃO DE USO", "PRÓPRIO MUNICIPAL - PERMISSÃO DE USO", "RECOMPRA", | |
"RECURSO ITBI", "REGULARIZAÇÃO", "REINTEGRAÇÃO DE POSSE", "SOLO CRIADO", "TAXA DE OCUPAÇÃO", | |
"USUCAPIÃO" | |
] | |
lista_imo = ["-", | |
"Apartamento", "Apartamento de cobertura", "Apartamento garden", "Armazém", "Bangalô", | |
"Barracão", "Box/Garagem", "Casa", "Casa comercial", "Casa em condomínio", | |
"Centro de distribuição", "Chácara", "Cobertura duplex", "Cobertura triplex", | |
"Condomínio de apartamentos", "Condomínio de casas", "Condomínio fechado", "Conjunto comercial", | |
"Duplex", "Edifício residencial", "Estúdio", "Fazenda", "Flat", "Galpão", "Gleba", "Hotel", | |
"Imóvel rural", "Imóvel urbano", "Kitnet", "Loft", "Loft duplex", "Loja", "Lote", "Motel", | |
"Ponto comercial", "Pousada/Chalé", "Prédio comercial", "Quarto", "Sala comercial", "Sobrado", | |
"Studio", "Sítio", "Terreno", "Terreno em condomínio", "Triplex", "Vila residencial", | |
"Outro" | |
] | |
#----------------------------------------------------------INTERFACES----------------------------------------------------------# | |
with gr.Blocks(theme=gr.themes.Monochrome(primary_hue="yellow", secondary_hue="yellow",)) as interface: | |
gr.Markdown(f""" | |
<p style="text-align: center; line-height: 1;"> | |
<b><span style='color: grey; font-size: 25px;'>aval</span></b> | |
<b><span style='color: orange; font-size: 25px;'>ia</span></b> | |
<b><span style='color: grey; font-size: 25px;'>.se</span></b> | |
</p> | |
<p style="text-align: center; line-height: 1.2;">Faça o download de uma planilha de exemplo <a href='https://huggingface.co/spaces/DavidSB/avalia.se_RL_Tabs/resolve/main/Teste.xlsx' download='Teste.xlsx'>aqui</a><br><br></p> | |
""") | |
with gr.Row(): | |
with gr.Column(): | |
with gr.Row(): | |
inp_1 = gr.File(label="Upload planilha", type="filepath", scale=1, height=100) | |
#inp_1 = gr.File(label="Upload planilha", type="filepath", scale=2, height=100) | |
with gr.Row(): | |
model = gr.Dropdown(['Gerar', 'Carregar',], label="Modelo", value='Gerar', scale=0.5) | |
inp_2 = gr.Textbox(label="Nome do modelo", scale=1, value='nome modelo') | |
inp_3 = gr.Dropdown(['Valor total', 'Valor unitário',], label="Var Dependente", value='Valor unitário') | |
inp_4 = gr.Dropdown(['y', 'lny', '1/y', 'y²'], label="Escala", value='y', scale=0.5) | |
button_1 = gr.Button("Gerar") | |
with gr.Group(): | |
with gr.Row(): | |
inp_5 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_1", value='x', scale=1) | |
inp_6 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_2", value='x', scale=1) | |
inp_7 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_3", value='-', scale=1) | |
inp_8 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_4", value='-', scale=1) | |
with gr.Row(): | |
inp_9 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_5", value='-', scale=1) | |
inp_10 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_6", value='-', scale=1) | |
inp_11 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_7", value='-', scale=1) | |
inp_12 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_8", value='-', scale=1) | |
with gr.Row(): | |
inp_13 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_9", value='-', scale=1) | |
inp_14 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_10", value='-', scale=1) | |
inp_15 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_11", value='-', scale=1) | |
inp_16 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_12", value='-', scale=1) | |
with gr.Row(): | |
inp_17 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_13", value='-', scale=1) | |
inp_18 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_14", value='-', scale=1) | |
inp_19 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_15", value='-', scale=1) | |
inp_20 = gr.Dropdown(['-','x', 'lnx', '1/x', 'x²'], label="Var_16", value='-', scale=1) | |
inp_21 = gr.Textbox(label="Manipular dados (separados por vírgula)", type="text", info = "Após rodar o modelo a primeira vez, por meio deste campo podem ser retirados outliers, pontos influenciantes, etc") | |
button_2 = gr.Button("Gerar") | |
with gr.Row(): | |
# Informações iniciais sobre o trabalho técnico | |
lau_1 = gr.Textbox(label="Identificação do trabalho técnico", value="-") | |
lau_2 = gr.Textbox(label="Data de Referência da Avaliação", value="-") | |
lau_3 = gr.Textbox(label="Data de elaboração da Avaliação", value="-") | |
with gr.Row(): | |
# Informações do Responsável Técnico | |
inf_1 = gr.Textbox(label="Responsável Técnico", value="-") | |
inf_2 = gr.Dropdown(["-", "Engenheiro Civil", "Arquiteto e Urbanista", "Corretor de Imóveis"], label="Profissão", value="-", | |
allow_custom_value=True) | |
with gr.Row(): | |
inf_3 = gr.Dropdown(["CREA", "CAU", "CRECI"],label="Entidade de Classe", value="-") | |
inf_4 = gr.Dropdown(["AC", "AL", "AP", "AM", "BA", "CE", "DF", "ES", "GO", "MA", "MT", "MS", "MG", "PA", "PB", "PR", "PE", "PI", "RJ", "RN", "RS", "RO", "RR", "SC", "SP", "SE", "TO"],label="Unidade Federativa", value="RS") | |
inf_5 = gr.Textbox(label="Nº do registro", value="-") | |
with gr.Row(): | |
# Introdução | |
int_1 = gr.Textbox(label="Endereço (Logradouro, nº e bairro)", value="-") | |
int_2 = gr.Textbox(label="Município", value="-") | |
with gr.Row(): | |
int_3 = gr.Dropdown(label="Tipo de Imóvel", choices = lista_imo, value="-", allow_custom_value=True) | |
int_4 = gr.Textbox(label="Solicitante", value="-") | |
with gr.Row(): | |
int_5 = gr.Dropdown(label="Finalidade", choices = lista_finalidades, value="-", allow_custom_value=True) | |
int_6 = gr.Textbox(label="Objetivo", value="-") | |
with gr.Row(): | |
# Características da Região | |
car_1 = gr.Textbox(label="Pressupostos, Ressalvas e Fatores Limitantes", value="-") | |
with gr.Row(): | |
car_2 = gr.Dropdown(["Água Potável", "Energia Elétrica", "Telefone", "Pavimentação", "Esgoto Pluvial", "Esgoto Cloacal" | |
"Iluminação Pública"], value=["Água Potável"], multiselect=True, label="Infraestrutura Urbana") | |
car_3 = gr.Dropdown(["Coleta de Lixo", "Transporte Coletivo", "Comércio", "Educação", "Saúde"], | |
value=["Coleta de Lixo"], multiselect=True, label="Serviços Públicos") | |
with gr.Row(): | |
car_4 = gr.Dropdown(["Residencial", "Comercial", "Misto"], label="Região - Uso",value="Residencial") | |
car_5 = gr.Dropdown(["Baixo", "Normal", "Alto"], label="Região - Padrão",value="Normal") | |
car_6 = gr.Dropdown(["Local", "Coletora", "Arterial"], label="Via de acesso ao imóvel",value="Local") | |
with gr.Row(): | |
car_7 = gr.Textbox(label="Outras inforações relevantes da região", value="-") | |
with gr.Row(): | |
# Diagnóstico de Mercado | |
dia_1 = gr.Dropdown(["Aparentemente aquecido", "Sem destaque", "Aparentemente recessivo"], label="Performance",value="Sem destaque") | |
dia_2 = gr.Dropdown(["Aparentemente alto", "Sem destaque", "Aparentemente baixo"], label="Nível de Ofertas do Segmento",value="Sem destaque") | |
dia_3 = gr.Dropdown(["Provavelmente alto", "Sem destaque", "Provavelmente baixo"], label="Liquidez",value="Sem destaque") | |
with gr.Row(): | |
dia_4 = gr.Textbox(label="Outras informações relevantes do Diagnóstico de mercado", value="-") | |
button_3 = gr.Button("Gerar") | |
with gr.Column(): | |
#out_1 = gr.Dataframe(label="Planilha de dados original", height=300) | |
out_2 = gr.Textbox(label="Colunas", scale=1) | |
out_3 = gr.Textbox(label="Resultados Gerais do Modelo", scale=1, lines=26) # Define o número de linhas para aumentar a altura | |
out_4 = gr.Textbox(label="Equação do Modelo") | |
out_5 = gr.Dataframe(label="Resultados por variável", height=250) | |
out_6 = gr.Dataframe(label="Planilha Regressão Linear (Variáveis e escalas escolhidas, sem outliers com o comparativo Obs x Calc)", height=250) | |
with gr.Group(): | |
with gr.Row(): | |
out_7 = gr.Textbox(label="Dados com resíduos padronizados > 2") | |
out_8 = gr.Textbox(label="Pontos Influenciantes (Distância de Cook > 1)") | |
out_9 = gr.Dataframe(label="Resíduos Padronizados > 2", height=250) | |
out_10 = gr.Dataframe(label="Outliers (retirados)", height=250) | |
#out_11 = gr.Dataframe(label="Valores Ajustados x Preços Observados", height=250) | |
out_12 = gr.Dataframe(label="Máximos e Mínimos por variável", height=250) | |
#button_4 = gr.Button("Gerar") | |
out_13 = gr.Image(show_label=False) | |
out_13a = gr.Image(show_label=False) | |
out_13b = gr.Image(show_label=False) | |
out_13c = gr.Image(show_label=False) | |
out_13d = gr.Image(show_label=False) | |
out_14 = gr.Dataframe(label="Avaliação", height=250) | |
out_15 = gr.components.File(label="Resultado da Avaliação") | |
out_16 = gr.components.File(label="Exportar Modelo") | |
with gr.Group(): | |
out_17 = gr.Plot(label="Gráfico Dispersão var 1", show_label=False) | |
out_18 = gr.Plot(label="Gráfico Dispersão var 2", show_label=False) | |
out_19 = gr.Plot(label="Gráfico Dispersão var 3", show_label=False) | |
out_20 = gr.Plot(label="Gráfico Dispersão var 4", show_label=False) | |
out_21 = gr.Plot(label="Gráfico Dispersão var 5", show_label=False) | |
out_22 = gr.Plot(label="Gráfico Dispersão var 6", show_label=False) | |
out_23 = gr.Plot(label="Gráfico Dispersão var 7", show_label=False) | |
out_24 = gr.Plot(label="Gráfico Dispersão var 8", show_label=False) | |
out_25 = gr.Plot(label="Gráfico Dispersão var 9", show_label=False) | |
out_26 = gr.Plot(label="Gráfico Dispersão var 10", show_label=False) | |
out_27 = gr.Plot(label="Gráfico Dispersão var 11", show_label=False) | |
out_28 = gr.Plot(label="Gráfico Dispersão var 12", show_label=False) | |
out_29 = gr.Plot(label="Gráfico Dispersão var 13", show_label=False) | |
out_30 = gr.Plot(label="Gráfico Dispersão var 14", show_label=False) | |
out_31 = gr.Plot(label="Gráfico Dispersão var 15", show_label=False) | |
out_32 = gr.Plot(label="Gráfico Dispersão var 16", show_label=False) | |
out_lau_7 = gr.Textbox(label = "Trabalho") | |
out_lau_1 = gr.Textbox(label = "Informações do Responsável Técnico") | |
out_lau_2 = gr.Textbox(label = "Introdução") | |
out_lau_3 = gr.Textbox(label = "Características da Região") | |
out_lau_4 = gr.Textbox(label = "Diagnóstico de Mercado") | |
out_lau_5 = gr.Textbox(label = "Metodologia") | |
out_lau_6 = gr.File(label="Laudo de Avaliação") | |
inputs = [ | |
inp_1, model, inp_2, inp_3, inp_4, inp_5, inp_6, inp_7, inp_8, inp_9, inp_10, inp_11, | |
inp_12, inp_13, inp_14, inp_15, inp_16, inp_17, inp_18, inp_19, inp_20, inp_21, | |
lau_1, lau_2, lau_3, | |
inf_1, inf_2, inf_3, inf_4, inf_5, | |
int_1, int_2, int_3, int_4, int_5, int_6, | |
car_1, car_2, car_3, car_4, car_5, car_6, car_7, | |
dia_1, dia_2, dia_3, dia_4 | |
] | |
outputs = [ | |
#out_1, | |
out_2, out_3, out_4, out_5, out_6, out_7, out_8, out_9, out_10, | |
out_12, out_13,out_13a,out_13b,out_13c,out_13d, out_14, out_15, out_16, out_17, out_18, out_19, out_20, | |
out_21, out_22, out_23, out_24, out_25, out_26, | |
out_27, out_28, out_29, out_30, out_31, out_32, | |
out_lau_7, out_lau_1, out_lau_2, out_lau_3, out_lau_4, out_lau_5, out_lau_6 | |
] | |
button_1.click(gera_model, inputs=inputs, outputs=outputs) | |
button_2.click(gera_model, inputs=inputs, outputs=outputs) | |
button_3.click(gera_model, inputs=inputs, outputs=outputs) | |
#button_4.click(gera_model, inputs=inputs, outputs=outputs) | |
if __name__ == "__main__": | |
interface.launch(debug=True) |