Testes: test_ajustecurvas

Testes para o módulo codigos.ajustecurvas.

Cobre mínimos quadrados (linear e ordem n), cálculo de Chi²/R², validações básicas e execução silenciosa (verbose=False).

Conteúdo dos testes:

  1"""Testes para o módulo `codigos.ajustecurvas`.
  2
  3Cobre mínimos quadrados (linear e ordem n), cálculo de Chi²/R², validações
  4básicas e execução silenciosa (verbose=False).
  5"""
  6
  7import numpy as np
  8from codigos import ajustecurvas as ac
  9
 10
 11def test_calcula_chi_e_r2_perfect_linear():
 12    """Verifica que métricas (Desvio, Chi², R²) indicam ajuste perfeito para reta exata."""
 13    x = np.array([0.0, 1.0, 2.0])
 14    y = 1.0 + 2.0 * x  # y = 2x + 1
 15    stats = ac.calcula_chi_e_r2(x, y, b0=1.0, b1=2.0, n_params=2, verbose=False)
 16    assert abs(stats['Desvio']) < 1e-12
 17    assert abs(stats['Chi2']) < 1e-12
 18    assert abs(stats['R2'] - 1.0) < 1e-12
 19
 20
 21def test_minquadrados_coefficients():
 22    """Verifica que o cálculo de coeficientes por fórmula produz R² ≈ 1 em dados perfeitos."""
 23    x = np.array([0.0, 1.0, 2.0, 3.0])
 24    y = 1.0 + 2.0 * x
 25    n = len(x)
 26    sum_x = np.sum(x)
 27    sum_y = np.sum(y)
 28    sum_xy = np.sum(x * y)
 29    sum_x2 = np.sum(x ** 2)
 30    b1 = (sum_x * sum_y - n * sum_xy) / ((sum_x) ** 2 - n * sum_x2)
 31    b0 = (sum_y - b1 * sum_x) / n
 32
 33    stats = ac.calcula_chi_e_r2(x, y, b0=b0, b1=b1, verbose=False)
 34    assert abs(stats['R2'] - 1.0) < 1e-12
 35
 36
 37def test_tabela_minimos_quadrados_runs_without_error():
 38    """Garante que a função de impressão de tabela não lança exceções (modo silencioso)."""
 39    x = np.array([0.0, 1.0, 2.0])
 40    y = np.array([1.0, 3.0, 5.0])
 41    ac.tabela_minimos_quadrados(x, y, verbose=False)
 42
 43
 44def test_minquadrados_ordem_n_quadratic():
 45    """Ajuste polinomial de ordem 2 recupera coeficientes exatos em dados sintéticos."""
 46    x = np.array([0.0, 1.0, 2.0, 3.0, 4.0])
 47    y = 1.0 + 2.0 * x + 3.0 * (x ** 2)
 48    coef = ac.minquadrados_ordem_n(x, y, ordem=2, tabela=False, grafico=False, verbose=False)
 49    assert coef is not None
 50    assert abs(coef[0] - 1.0) < 1e-8
 51    assert abs(coef[1] - 2.0) < 1e-8
 52    assert abs(coef[2] - 3.0) < 1e-8
 53
 54
 55def test_minquadrados_ordem_n_linear():
 56    """Ajuste linear recupera coeficientes exatos em dados sintéticos."""
 57    x = np.array([0.0, 1.0, 2.0, 3.0])
 58    y = 1.0 + 2.0 * x
 59    coef = ac.minquadrados_ordem_n(x, y, ordem=1, tabela=False, grafico=False, verbose=False)
 60    assert coef is not None
 61    assert abs(coef[0] - 1.0) < 1e-10
 62    assert abs(coef[1] - 2.0) < 1e-10
 63
 64
 65def test_minquadrados_ordem_n_cubic():
 66    """Ajuste cúbico recupera coeficientes exatos em dados sintéticos."""
 67    x = np.array([0.0, 1.0, 2.0, 3.0, 4.0, 5.0])
 68    y = 1.0 + 2.0 * x + 3.0 * (x ** 2) + 4.0 * (x ** 3)
 69    coef = ac.minquadrados_ordem_n(x, y, ordem=3, tabela=False, grafico=False, verbose=False)
 70    assert coef is not None
 71    assert abs(coef[0] - 1.0) < 1e-6
 72    assert abs(coef[1] - 2.0) < 1e-6
 73    assert abs(coef[2] - 3.0) < 1e-6
 74    assert abs(coef[3] - 4.0) < 1e-6
 75
 76
 77def test_calcula_chi_e_r2_imperfect_fit():
 78    """Dados não perfeitos devem resultar em R² < 1 e Chi² > 0."""
 79    x = np.array([0.0, 1.0, 2.0])
 80    y = np.array([1.0, 3.1, 5.2])
 81    stats = ac.calcula_chi_e_r2(x, y, b0=1.0, b1=2.0, n_params=2, verbose=False)
 82    assert stats['R2'] < 1.0 
 83    assert stats['Chi2'] > 0
 84
 85
 86def test_minquadrados_silent():
 87    """Verifica que minquadrados executa sem imprimir em modo silencioso."""
 88    x = np.array([0.0, 1.0, 2.0, 3.0])
 89    y = 1.0 + 2.0 * x
 90    ac.minquadrados(x, y, verbose=False, tabela=False, grafico=False)
 91
 92
 93def test_input_validation_errors():
 94    """Valida que validações de entrada levantam erros apropriados."""
 95    import pytest
 96    
 97    with pytest.raises(ValueError, match="x e y devem ter o mesmo comprimento"):
 98        ac._validate_curve_fitting_inputs([1, 2], [1, 2, 3])
 99    
100    with pytest.raises(ValueError, match="São necessários pelo menos 2 pontos para ajuste de curvas"):
101        ac._validate_curve_fitting_inputs([1], [1])
102
103
104def test_minquadrados_height_weight_dataset():
105    """Exemplo prático: ajuste de altura x peso (aceita execução sem exceção)."""
106    x = np.array([183, 173, 168, 188, 158, 163, 193, 163, 178])
107    y = np.array([79, 69, 70, 81, 61, 63, 79, 71, 73])
108    
109    ac.minquadrados(x, y, verbose=False, tabela=False, grafico=False)
110
111
112def test_minquadrados_linear_dataset_7_points():
113    """Valida execução em conjunto de 7 pontos (no-throw)."""
114    x = np.array([1, 2, 3, 4, 5, 6, 7])
115    y = np.array([0.5, 0.6, 0.9, 0.8, 1.2, 1.5, 1.7])
116
117    ac.minquadrados(x, y, verbose=False, tabela=False, grafico=False)
118
119
120def test_minquadrados_linear_dataset_8_points():
121    """Valida execução em conjunto de 8 pontos (no-throw)."""
122    x = np.array([1, 2, 3, 4, 5, 6, 7, 8])
123    y = np.array([0.5, 0.6, 0.9, 0.8, 1.2, 1.5, 1.7, 2.0])
124    
125    ac.minquadrados(x, y, verbose=False, tabela=False, grafico=False)
126
127
128def test_minquadrados_linear_dataset_10_points():
129    """Valida execução em conjunto de 10 pontos (no-throw)."""
130    x = np.array([0, 2, 4, 6, 9, 11, 12, 15, 17, 19])
131    y = np.array([5, 6, 7, 6, 9, 8, 7, 10, 12, 12])
132    
133    ac.minquadrados(x, y, verbose=False, tabela=False, grafico=False)
134
135
136def test_minquadrados_negative_slope_dataset():
137    """Valida execução para conjunto com declive negativo (no-throw)."""
138    x = np.array([1.4, 2.1, 3.0, 4.4])
139    y = np.array([4.2, 2.3, 1.9, 1.1])
140    
141    ac.minquadrados(x, y, verbose=False, tabela=False, grafico=False)
142
143
144def test_minquadrados_ordem_n_quadratic_user_example():
145    """Ajuste polinomial de ordem n em exemplo fornecido pelo usuário."""
146    x = np.array([-3, -1, 1, 2, 3])
147    y = np.array([-1, 0, 1, 1, -1])
148    
149    coef = ac.minquadrados_ordem_n(x, y, ordem=2, tabela=False, grafico=False, verbose=False)
150    assert coef is not None
151    assert len(coef) == 3

Resumo das funções de teste:

  • test_calcula_chi_e_r2_perfect_linear: Verifica que métricas (Desvio, Chi², R²) indicam ajuste perfeito para reta exata.

  • test_minquadrados_coefficients: Verifica que o cálculo de coeficientes por fórmula produz R² ≈ 1 em dados perfeitos.

  • test_tabela_minimos_quadrados_runs_without_error: Garante que a função de impressão de tabela não lança exceções (modo silencioso).

  • test_minquadrados_ordem_n_quadratic: Ajuste polinomial de ordem 2 recupera coeficientes exatos em dados sintéticos.

  • test_minquadrados_ordem_n_linear: Ajuste linear recupera coeficientes exatos em dados sintéticos.

  • test_minquadrados_ordem_n_cubic: Ajuste cúbico recupera coeficientes exatos em dados sintéticos.

  • test_calcula_chi_e_r2_imperfect_fit: Dados não perfeitos devem resultar em R² < 1 e Chi² > 0.

  • test_minquadrados_silent: Verifica que minquadrados executa sem imprimir em modo silencioso.

  • test_input_validation_errors: Valida que validações de entrada levantam erros apropriados.

  • test_minquadrados_height_weight_dataset: Exemplo prático: ajuste de altura x peso (aceita execução sem exceção).

  • test_minquadrados_linear_dataset_7_points: Valida execução em conjunto de 7 pontos (no-throw).

  • test_minquadrados_linear_dataset_8_points: Valida execução em conjunto de 8 pontos (no-throw).

  • test_minquadrados_linear_dataset_10_points: Valida execução em conjunto de 10 pontos (no-throw).

  • test_minquadrados_negative_slope_dataset: Valida execução para conjunto com declive negativo (no-throw).

  • test_minquadrados_ordem_n_quadratic_user_example: Ajuste polinomial de ordem n em exemplo fornecido pelo usuário.