C2MV commited on
Commit
57bbc39
verified
1 Parent(s): 44eec3f

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +71 -100
app.py CHANGED
@@ -62,7 +62,7 @@ class RSM_BoxBehnken:
62
  self.model = smf.ols(formula, data=self.data).fit()
63
  print("Modelo Completo:")
64
  print(self.model.summary())
65
- return self.model, self.pareto_chart(self.model, "Pareto - Modelo Completo")
66
 
67
  def fit_simplified_model(self):
68
  """
@@ -73,8 +73,8 @@ class RSM_BoxBehnken:
73
  self.model_simplified = smf.ols(formula, data=self.data).fit()
74
  print("\nModelo Simplificado:")
75
  print(self.model_simplified.summary())
76
- return self.model_simplified, self.pareto_chart(self.model_simplified, "Pareto - Modelo Simplificado")
77
-
78
  def optimize(self, method='Nelder-Mead'):
79
  """
80
  Encuentra los niveles 贸ptimos de los factores para maximizar la respuesta usando el modelo simplificado.
@@ -266,18 +266,20 @@ class RSM_BoxBehnken:
266
  levels = self.get_levels(variable_name)
267
  return -1 + 2 * (natural_value - levels[0]) / (levels[-1] - levels[0])
268
 
269
- def pareto_chart(self, model, title):
270
  """
271
  Genera un diagrama de Pareto para los efectos usando estad铆sticos F,
272
  incluyendo la l铆nea de significancia.
273
  """
274
  # Calcular los estad铆sticos F para cada t茅rmino
275
- # F = (coef/std_err)^2 = t^2
276
- fvalues = model.tvalues[1:]**2 # Excluir la Intercept y convertir t a F
277
  abs_fvalues = np.abs(fvalues)
278
  sorted_idx = np.argsort(abs_fvalues)[::-1]
279
  sorted_fvalues = abs_fvalues[sorted_idx]
280
  sorted_names = fvalues.index[sorted_idx]
 
 
 
281
 
282
  # Calcular el valor cr铆tico de F para la l铆nea de significancia
283
  alpha = 0.05 # Nivel de significancia
@@ -301,6 +303,43 @@ class RSM_BoxBehnken:
301
  annotation_position="bottom right")
302
 
303
  return fig
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
304
 
305
  def get_simplified_equation(self):
306
  """
@@ -343,81 +382,9 @@ class RSM_BoxBehnken:
343
 
344
  return self.data[[self.y_name, 'Predicho', 'Residual']].round(3)
345
 
346
- def calculate_contribution_percentage(self):
347
  """
348
- Calcula el porcentaje de contribuci贸n de cada factor usando estad铆sticos F.
349
- """
350
- if self.model_simplified is None:
351
- print("Error: Ajusta el modelo simplificado primero.")
352
- return None
353
-
354
- # ANOVA del modelo simplificado
355
- anova_table = sm.stats.anova_lm(self.model_simplified, typ=2)
356
-
357
- # Suma de cuadrados total
358
- ss_total = anova_table['sum_sq'].sum()
359
-
360
- # Crear tabla de contribuci贸n
361
- contribution_table = pd.DataFrame({
362
- 'Fuente de Variaci贸n': [],
363
- 'Suma de Cuadrados': [],
364
- 'Grados de Libertad': [],
365
- 'Cuadrado Medio': [],
366
- 'F': [],
367
- 'Valor p': [],
368
- '% Contribuci贸n': []
369
- })
370
-
371
- # Calcular estad铆sticos F y porcentaje de contribuci贸n para cada factor
372
- ms_error = anova_table.loc['Residual', 'sum_sq'] / anova_table.loc['Residual', 'df']
373
-
374
- for index, row in anova_table.iterrows():
375
- if index != 'Residual':
376
- factor_name = index
377
- if factor_name == f'I({self.x1_name} ** 2)':
378
- factor_name = f'{self.x1_name}^2'
379
- elif factor_name == f'I({self.x2_name} ** 2)':
380
- factor_name = f'{self.x2_name}^2'
381
- elif factor_name == f'I({self.x3_name} ** 2)':
382
- factor_name = f'{self.x3_name}^2'
383
-
384
- ss_factor = row['sum_sq']
385
- df_factor = row['df']
386
- ms_factor = ss_factor / df_factor
387
- f_stat = ms_factor / ms_error
388
- p_value = f.sf(f_stat, df_factor, anova_table.loc['Residual', 'df'])
389
- contribution_percentage = (ss_factor / ss_total) * 100
390
-
391
- contribution_table = pd.concat([contribution_table, pd.DataFrame({
392
- 'Fuente de Variaci贸n': [factor_name],
393
- 'Suma de Cuadrados': [ss_factor],
394
- 'Grados de Libertad': [df_factor],
395
- 'Cuadrado Medio': [ms_factor],
396
- 'F': [f_stat],
397
- 'Valor p': [p_value],
398
- '% Contribuci贸n': [contribution_percentage]
399
- })], ignore_index=True)
400
-
401
- # Calcular estad铆stico F global y su valor p
402
- f_global = anova_table['sum_sq'][:-1].sum() / anova_table['df'][:-1].sum() / ms_error
403
- p_global = f.sf(f_global, anova_table['df'][:-1].sum(), anova_table.loc['Residual', 'df'])
404
-
405
- # Agregar fila para el estad铆stico F global
406
- contribution_table = pd.concat([contribution_table, pd.DataFrame({
407
- 'Fuente de Variaci贸n': ['F global'],
408
- 'Suma de Cuadrados': [np.nan],
409
- 'Grados de Libertad': [np.nan],
410
- 'Cuadrado Medio': [np.nan],
411
- 'F': [f_global],
412
- 'Valor p': [p_global],
413
- '% Contribuci贸n': [np.nan]
414
- })], ignore_index=True)
415
-
416
- return contribution_table.round(3)
417
-
418
- def calculate_detailed_anova(self):
419
- """
420
- Calcula la tabla ANOVA detallada con la descomposici贸n del error residual.
421
  """
422
  if self.model_simplified is None:
423
  print("Error: Ajusta el modelo simplificado primero.")
@@ -502,6 +469,9 @@ class RSM_BoxBehnken:
502
  f_curvature,
503
  p_curvature
504
  ]
 
 
 
505
 
506
  # Reorganizar las filas y resetear el 铆ndice
507
  detailed_anova_table = detailed_anova_table.reindex([0, 5, 1, 2, 3, 4]).reset_index(drop=True)
@@ -513,13 +483,11 @@ class RSM_BoxBehnken:
513
  Obtiene todas las tablas generadas para ser exportadas a Excel.
514
  """
515
  prediction_table = self.generate_prediction_table()
516
- contribution_table = self.calculate_contribution_percentage()
517
- detailed_anova_table = self.calculate_detailed_anova()
518
 
519
  return {
520
  'Predicciones': prediction_table,
521
- '% Contribuci贸n': contribution_table,
522
- 'ANOVA Detallada': detailed_anova_table
523
  }
524
 
525
  def save_figures_to_zip(self):
@@ -672,16 +640,15 @@ def load_data(x1_name, x2_name, x3_name, y_name, x1_levels_str, x2_levels_str, x
672
 
673
  def fit_and_optimize_model():
674
  if 'rsm' not in globals():
675
- return [None]*11 # Ajustar el n煤mero de outputs
676
 
677
  # Ajustar modelos y optimizar
678
- model_completo, pareto_completo = rsm.fit_model()
679
- model_simplificado, pareto_simplificado = rsm.fit_simplified_model()
680
  optimization_table = rsm.optimize()
681
  equation = rsm.get_simplified_equation()
682
  prediction_table = rsm.generate_prediction_table()
683
- contribution_table = rsm.calculate_contribution_percentage()
684
- anova_table = rsm.calculate_detailed_anova()
685
 
686
  # Generar todas las figuras y almacenarlas
687
  rsm.generate_all_plots()
@@ -698,13 +665,14 @@ def fit_and_optimize_model():
698
 
699
  return (
700
  model_completo.summary().as_html(),
701
- pareto_completo,
 
702
  model_simplificado.summary().as_html(),
703
- pareto_simplificado,
 
704
  equation_formatted,
705
  optimization_table,
706
  prediction_table,
707
- contribution_table,
708
  anova_table,
709
  zip_path, # Ruta del ZIP de gr谩ficos
710
  excel_path # Ruta del Excel de tablas
@@ -831,16 +799,17 @@ def create_gradio_interface():
831
  fit_button = gr.Button("Ajustar Modelo y Optimizar")
832
  gr.Markdown("**Modelo Completo**")
833
  model_completo_output = gr.HTML()
834
- pareto_completo_output = gr.Plot()
 
835
  gr.Markdown("**Modelo Simplificado**")
836
  model_simplificado_output = gr.HTML()
837
- pareto_simplificado_output = gr.Plot()
 
838
  gr.Markdown("**Ecuaci贸n del Modelo Simplificado**")
839
  equation_output = gr.HTML()
840
  optimization_table_output = gr.Dataframe(label="Tabla de Optimizaci贸n", interactive=False)
841
  prediction_table_output = gr.Dataframe(label="Tabla de Predicciones", interactive=False)
842
- contribution_table_output = gr.Dataframe(label="Tabla de % de Contribuci贸n", interactive=False)
843
- anova_table_output = gr.Dataframe(label="Tabla ANOVA Detallada", interactive=False)
844
  gr.Markdown("## Descargar Todas las Tablas")
845
  download_excel_button = gr.DownloadButton("Descargar Tablas en Excel")
846
  download_word_button = gr.DownloadButton("Descargar Tablas en Word")
@@ -874,13 +843,14 @@ def create_gradio_interface():
874
  inputs=[],
875
  outputs=[
876
  model_completo_output,
877
- pareto_completo_output,
 
878
  model_simplificado_output,
879
- pareto_simplificado_output,
 
880
  equation_output,
881
  optimization_table_output,
882
  prediction_table_output,
883
- contribution_table_output,
884
  anova_table_output,
885
  download_all_plots_button, # Ruta del ZIP de gr谩ficos
886
  download_excel_button # Ruta del Excel de tablas
@@ -961,4 +931,5 @@ def main():
961
  interface.launch(share=True)
962
 
963
  if __name__ == "__main__":
964
- main()
 
 
62
  self.model = smf.ols(formula, data=self.data).fit()
63
  print("Modelo Completo:")
64
  print(self.model.summary())
65
+ return self.model, self.pareto_chart_f(self.model, "Pareto - Modelo Completo (F)"), self.pareto_chart_t(self.model, "Pareto - Modelo Completo (t)")
66
 
67
  def fit_simplified_model(self):
68
  """
 
73
  self.model_simplified = smf.ols(formula, data=self.data).fit()
74
  print("\nModelo Simplificado:")
75
  print(self.model_simplified.summary())
76
+ return self.model_simplified, self.pareto_chart_f(self.model_simplified, "Pareto - Modelo Simplificado (F)"), self.pareto_chart_t(self.model_simplified, "Pareto - Modelo Simplificado (t)")
77
+
78
  def optimize(self, method='Nelder-Mead'):
79
  """
80
  Encuentra los niveles 贸ptimos de los factores para maximizar la respuesta usando el modelo simplificado.
 
266
  levels = self.get_levels(variable_name)
267
  return -1 + 2 * (natural_value - levels[0]) / (levels[-1] - levels[0])
268
 
269
+ def pareto_chart_f(self, model, title):
270
  """
271
  Genera un diagrama de Pareto para los efectos usando estad铆sticos F,
272
  incluyendo la l铆nea de significancia.
273
  """
274
  # Calcular los estad铆sticos F para cada t茅rmino
275
+ fvalues = model.fvalues[1:] # Excluir la Intercept
 
276
  abs_fvalues = np.abs(fvalues)
277
  sorted_idx = np.argsort(abs_fvalues)[::-1]
278
  sorted_fvalues = abs_fvalues[sorted_idx]
279
  sorted_names = fvalues.index[sorted_idx]
280
+
281
+ # Cambiar I() por "" en los nombres de los terminos
282
+ sorted_names = sorted_names.str.replace('I(','').str.replace('**2)','^2').str.replace(' * ', '路')
283
 
284
  # Calcular el valor cr铆tico de F para la l铆nea de significancia
285
  alpha = 0.05 # Nivel de significancia
 
303
  annotation_position="bottom right")
304
 
305
  return fig
306
+
307
+ def pareto_chart_t(self, model, title):
308
+ """
309
+ Genera un diagrama de Pareto para los efectos usando estad铆sticos t,
310
+ incluyendo la l铆nea de significancia.
311
+ """
312
+ # Calcular los estad铆sticos t para cada t茅rmino
313
+ tvalues = model.tvalues[1:] # Excluir la Intercept
314
+ abs_tvalues = np.abs(tvalues)
315
+ sorted_idx = np.argsort(abs_tvalues)[::-1]
316
+ sorted_tvalues = abs_tvalues[sorted_idx]
317
+ sorted_names = tvalues.index[sorted_idx]
318
+
319
+ # Cambiar I() por "" en los nombres de los terminos
320
+ sorted_names = sorted_names.str.replace('I(','').str.replace('**2)','^2').str.replace(' * ', '路')
321
+
322
+ # Calcular el valor cr铆tico de t para la l铆nea de significancia
323
+ alpha = 0.05 # Nivel de significancia
324
+ dof = model.df_resid # Grados de libertad residuales
325
+ t_critical = t.ppf(1 - alpha / 2, dof)
326
+
327
+ # Crear el diagrama de Pareto
328
+ fig = px.bar(
329
+ x=sorted_tvalues.round(3),
330
+ y=sorted_names,
331
+ orientation='h',
332
+ labels={'x': 'Estad铆stico t', 'y': 'T茅rmino'},
333
+ title=title
334
+ )
335
+ fig.update_yaxes(autorange="reversed")
336
+
337
+ # Agregar la l铆nea de significancia
338
+ fig.add_vline(x=t_critical, line_dash="dot",
339
+ annotation_text=f"t cr铆tico = {t_critical:.3f}",
340
+ annotation_position="bottom right")
341
+
342
+ return fig
343
 
344
  def get_simplified_equation(self):
345
  """
 
382
 
383
  return self.data[[self.y_name, 'Predicho', 'Residual']].round(3)
384
 
385
+ def calculate_anova_table(self):
386
  """
387
+ Calcula la tabla ANOVA detallada, incluyendo la contribuci贸n porcentual.
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
388
  """
389
  if self.model_simplified is None:
390
  print("Error: Ajusta el modelo simplificado primero.")
 
469
  f_curvature,
470
  p_curvature
471
  ]
472
+
473
+ # --- Agregar % de Contribuci贸n ---
474
+ detailed_anova_table['% Contribuci贸n'] = (detailed_anova_table['Suma de Cuadrados'] / ss_total) * 100
475
 
476
  # Reorganizar las filas y resetear el 铆ndice
477
  detailed_anova_table = detailed_anova_table.reindex([0, 5, 1, 2, 3, 4]).reset_index(drop=True)
 
483
  Obtiene todas las tablas generadas para ser exportadas a Excel.
484
  """
485
  prediction_table = self.generate_prediction_table()
486
+ anova_table = self.calculate_anova_table()
 
487
 
488
  return {
489
  'Predicciones': prediction_table,
490
+ 'ANOVA': anova_table,
 
491
  }
492
 
493
  def save_figures_to_zip(self):
 
640
 
641
  def fit_and_optimize_model():
642
  if 'rsm' not in globals():
643
+ return [None]*12 # Ajustar el n煤mero de outputs
644
 
645
  # Ajustar modelos y optimizar
646
+ model_completo, pareto_completo_f, pareto_completo_t = rsm.fit_model()
647
+ model_simplificado, pareto_simplificado_f, pareto_simplificado_t = rsm.fit_simplified_model()
648
  optimization_table = rsm.optimize()
649
  equation = rsm.get_simplified_equation()
650
  prediction_table = rsm.generate_prediction_table()
651
+ anova_table = rsm.calculate_anova_table()
 
652
 
653
  # Generar todas las figuras y almacenarlas
654
  rsm.generate_all_plots()
 
665
 
666
  return (
667
  model_completo.summary().as_html(),
668
+ pareto_completo_f,
669
+ pareto_completo_t,
670
  model_simplificado.summary().as_html(),
671
+ pareto_simplificado_f,
672
+ pareto_simplificado_t,
673
  equation_formatted,
674
  optimization_table,
675
  prediction_table,
 
676
  anova_table,
677
  zip_path, # Ruta del ZIP de gr谩ficos
678
  excel_path # Ruta del Excel de tablas
 
799
  fit_button = gr.Button("Ajustar Modelo y Optimizar")
800
  gr.Markdown("**Modelo Completo**")
801
  model_completo_output = gr.HTML()
802
+ pareto_completo_f_output = gr.Plot()
803
+ pareto_completo_t_output = gr.Plot()
804
  gr.Markdown("**Modelo Simplificado**")
805
  model_simplificado_output = gr.HTML()
806
+ pareto_simplificado_f_output = gr.Plot()
807
+ pareto_simplificado_t_output = gr.Plot()
808
  gr.Markdown("**Ecuaci贸n del Modelo Simplificado**")
809
  equation_output = gr.HTML()
810
  optimization_table_output = gr.Dataframe(label="Tabla de Optimizaci贸n", interactive=False)
811
  prediction_table_output = gr.Dataframe(label="Tabla de Predicciones", interactive=False)
812
+ anova_table_output = gr.Dataframe(label="Tabla ANOVA", interactive=False)
 
813
  gr.Markdown("## Descargar Todas las Tablas")
814
  download_excel_button = gr.DownloadButton("Descargar Tablas en Excel")
815
  download_word_button = gr.DownloadButton("Descargar Tablas en Word")
 
843
  inputs=[],
844
  outputs=[
845
  model_completo_output,
846
+ pareto_completo_f_output,
847
+ pareto_completo_t_output,
848
  model_simplificado_output,
849
+ pareto_simplificado_f_output,
850
+ pareto_simplificado_t_output,
851
  equation_output,
852
  optimization_table_output,
853
  prediction_table_output,
 
854
  anova_table_output,
855
  download_all_plots_button, # Ruta del ZIP de gr谩ficos
856
  download_excel_button # Ruta del Excel de tablas
 
931
  interface.launch(share=True)
932
 
933
  if __name__ == "__main__":
934
+ main()
935
+