class_docstr: Test parametric.py.
class_docstr_tok: ["Test","parametric.py","."]
docstr: Test function anova.
  Compare results to JASP.
docstr_tok: ["Test","function","anova",".","Compare","results","to","JASP","."]
code: def test_anova(self):
      """Test function anova.
      Compare results to JASP.
      """
      # Pain dataset
      df_pain = read_dataset("anova")
      anova(dv="Pain threshold", between=["Hair color"], data=df_pain)
      # Compare with JASP
      aov = anova(
          dv="Pain threshold",
          between="Hair color",
          data=df_pain,
          detailed=True,
      ).round(3)
      assert aov.at[0, "F"] == 6.791
      assert aov.at[0, "p-unc"] == 0.004
      assert aov.at[0, "np2"] == 0.576
      aov = anova(
          dv="Pain threshold",
          between="Hair color",
          data=df_pain,
          effsize="n2",
          detailed=True,
      ).round(3)
      assert aov.at[0, "n2"] == 0.576
  
      # Unbalanced and with missing values
      df_pain.loc[[17, 18], "Pain threshold"] = np.nan
      aov = df_pain.anova(
          dv="Pain threshold", between="Hair color"
      ).round(3)
      assert aov.at[0, "ddof1"] == 3
      assert aov.at[0, "ddof2"] == 13
      assert aov.at[0, "F"] == 4.359
      assert aov.at[0, "p-unc"] == 0.025
      assert aov.at[0, "np2"] == 0.501
      # Error: between is an empty list
      with pytest.raises(ValueError):
          anova(dv="Pain threshold", between=[], data=df_pain)
  
      # Unbalanced and with missing values AND between as a categorical
      df_paincat = df_pain.copy()
      df_paincat["Hair color"] = df_paincat["Hair color"].astype(
          "category"
      )
      df_paincat["Hair color"] = df_paincat[
          "Hair color"
      ].cat.add_categories("Bald")
      aov = df_paincat.anova(
          dv="Pain threshold", between="Hair color"
      ).round(3)
      assert aov.at[0, "ddof1"] == 3
      assert aov.at[0, "ddof2"] == 13
      assert aov.at[0, "F"] == 4.359
      assert aov.at[0, "p-unc"] == 0.025
      assert aov.at[0, "np2"] == 0.501
  
      # Two-way ANOVA with balanced design
      df_aov2 = read_dataset("anova2")
      aov2 = anova(
          dv="Yield", between=["Blend", "Crop"], data=df_aov2
      ).round(4)
      array_equal(
          aov2.loc[:, "MS"], [2.0417, 1368.2917, 1180.0417, 541.8472]
      )
      array_equal(aov2.loc[[0, 1, 2], "F"], [0.0038, 2.5252, 2.1778])
      array_equal(
          aov2.loc[[0, 1, 2], "p-unc"], [0.9517, 0.1080, 0.1422]
      )
      array_equal(aov2.loc[[0, 1, 2], "np2"], [0.0002, 0.2191, 0.1948])
      # Same but with standard eta-square
      aov2 = anova(
          dv="Yield",
          between=["Blend", "Crop"],
          data=df_aov2,
          effsize="n2",
      ).round(4)
      array_equal(aov2.loc[[0, 1, 2], "n2"], [0.0001, 0.1843, 0.1589])
  
      # Two-way ANOVA with unbalanced design
      df_aov2 = read_dataset("anova2_unbalanced")
      aov2 = df_aov2.anova(
          dv="Scores", between=["Diet", "Exercise"]
      ).round(3)
      array_equal(aov2.loc[:, "MS"], [390.625, 180.625, 15.625, 52.625])
      array_equal(aov2.loc[[0, 1, 2], "F"], [7.423, 3.432, 0.297])
      array_equal(aov2.loc[[0, 1, 2], "p-unc"], [0.034, 0.113, 0.605])
      array_equal(aov2.loc[[0, 1, 2], "np2"], [0.553, 0.364, 0.047])
  
      # Two-way ANOVA with unbalanced design and missing values
      df_aov2.loc[9, "Scores"] = np.nan
      # Type 2
      aov2 = anova(
          dv="Scores", between=["Diet", "Exercise"], data=df_aov2
      ).round(3)
      array_equal(aov2.loc[[0, 1, 2], "F"], [10.403, 5.167, 0.761])
      array_equal(aov2.loc[[0, 1, 2], "p-unc"], [0.023, 0.072, 0.423])
      array_equal(aov2.loc[[0, 1, 2], "np2"], [0.675, 0.508, 0.132])
      # Type 1
      aov2_ss1 = anova(
          dv="Scores",
          between=["Diet", "Exercise"],
          ss_type=1,
          data=df_aov2,
      ).round(3)
      assert not aov2.equals(aov2_ss1)
  
      # Three-way ANOVA using statsmodels
      # Balanced
      df_aov3 = read_dataset("anova3")
      aov3_ss1 = anova(
          dv="Cholesterol",
          between=["Sex", "Risk", "Drug"],
          ss_type=1,
          data=df_aov3,
      ).round(3)
      aov3_ss2 = anova(
          dv="Cholesterol",
          between=["Sex", "Risk", "Drug"],
          ss_type=2,
          data=df_aov3,
      ).round(3)
      aov3_ss3 = anova(
          dv="Cholesterol",
          between=["Sex", "Risk", "Drug"],
          ss_type=3,
          data=df_aov3,
      ).round(3)
      # Check that type 1 == type 2 == type 3
      assert aov3_ss1.equals(aov3_ss2)
      assert aov3_ss2.equals(aov3_ss3)
      # Compare with JASP
      array_equal(
          aov3_ss1.loc[:, "F"],
          [2.462, 13.449, 0.484, 0.139, 1.522, 1.446, 1.094, np.nan],
      )
      array_equal(
          aov3_ss1.loc[:, "np2"],
          [0.049, 0.219, 0.020, 0.003, 0.060, 0.057, 0.044, np.nan],
      )
      array_equal(
          aov3_ss1.loc[:, "p-unc"],
          [0.123, 0.001, 0.619, 0.711, 0.229, 0.245, 0.343, np.nan],
      )
      # Unbalanced
      df_aov3 = read_dataset("anova3_unbalanced")
      aov3_ss1 = anova(
          dv="Cholesterol",
          between=["Sex", "Risk", "Drug"],
          ss_type=1,
          data=df_aov3,
      ).round(3)
      aov3_ss2 = anova(
          dv="Cholesterol",
          between=["Sex", "Risk", "Drug"],
          ss_type=2,
          data=df_aov3,
      ).round(3)
      aov3_ss3 = anova(
          dv="Cholesterol",
          between=["Sex", "Risk", "Drug"],
          ss_type=3,
          data=df_aov3,
      ).round(3)
      # Compare with JASP
      # Type 1
      array_equal(
          aov3_ss1.loc[:, "F"],
          [4.155, 15.166, 0.422, 0.085, 0.859, 1.170, 0.505, np.nan],
      )
      array_equal(
          aov3_ss1.loc[:, "np2"],
          [0.068, 0.210, 0.015, 0.001, 0.029, 0.039, 0.017, np.nan],
      )
      array_equal(
          aov3_ss1.loc[:, "p-unc"],
          [0.046, 0.0, 0.658, 0.772, 0.429, 0.318, 0.606, np.nan],
      )
      array_equal(
          aov3_ss1.loc[:, "Source"],
          [
              "Sex",
              "Risk",
              "Drug",
              "Sex * Risk",
              "Sex * Drug",
              "Risk * Drug",
              "Sex * Risk * Drug",
              "Residual",
          ],
      )
      # Type 2
      array_equal(
          aov3_ss2.loc[:, "F"],
          [3.759, 15.169, 0.429, 0.099, 0.739, 1.170, 0.505, np.nan],
      )
      array_equal(
          aov3_ss2.loc[:, "np2"],
          [0.062, 0.210, 0.015, 0.002, 0.025, 0.039, 0.017, np.nan],
      )
      array_equal(
          aov3_ss2.loc[:, "p-unc"],
          [0.057, 0.0, 0.653, 0.754, 0.482, 0.318, 0.606, np.nan],
      )
  
      # Type 3
      array_equal(
          aov3_ss3.loc[:, "F"],
          [3.910, 15.555, 0.484, 0.079, 0.750, 1.060, 0.505, np.nan],
      )
      array_equal(
          aov3_ss3.loc[:, "np2"],
          [0.064, 0.214, 0.017, 0.001, 0.026, 0.036, 0.017, np.nan],
      )
      array_equal(
          aov3_ss3.loc[:, "p-unc"],
          [0.053, 0.0, 0.619, 0.779, 0.477, 0.353, 0.606, np.nan],
      )
  
      aov3_ss3 = anova(
          dv="Cholesterol",
          between=["Sex", "Risk", "Drug"],
          ss_type=3,
          data=df_aov3,
          effsize="n2",
      ).round(3)
      array_equal(
          aov3_ss3.loc[:, "n2"],
          [0.048, 0.189, 0.012, 0.001, 0.018, 0.026, 0.012, np.nan],
      )
  
      # Error: invalid char in column names
      df_aov3["Sex:"] = np.random.normal(size=df_aov3.shape[0])
      with pytest.raises(ValueError):
          anova(
              dv="Cholesterol",
              between=["Sex:", "Risk", "Drug"],
              data=df_aov3,
          )
  
file_path: pingouin/pingouin/tests/test_parametric.py
imports: import pytest
  import numpy
  from unittest import TestCase
  from numpy.testing import assert_array_equal
  from pingouin import read_dataset
  from pingouin.parametric import ttest, anova, rm_anova, mixed_anova, ancova, welch_anova
label_desc: Use image node_id 2 for calling the TestParametric obj's underlying member method code with example usage: obj.test_anova() without return types