code: def test_grid_generator_equalized_odds_basic(grid_limit):
      # Equalized odds has four rows with potential non-zero values in the grid.
      # grid_size = 5 ensures that each of the groups have their own column.
      grid_size = 5
  
      disparity_moment = EqualizedOdds()
      label0 = "label=0"
      label1 = "label=1"
      events = [label0, label1]
  
      grid = calculate_grid(grid_limit, grid_size, disparity_moment)
  
      expected_index = pd.MultiIndex.from_product(
          [["+", "-"], events, [0, 1]], names=[_SIGN, _EVENT, _GROUP_ID]
      )
      assert (expected_index == grid.index).all()
      expected_grid = pd.DataFrame()
      for i in range(grid_size):
          expected_grid[i] = pd.Series(0.0, index=expected_index)
  
      expected_grid[0]["-", label0, 1] = grid_limit
      expected_grid[1]["-", label1, 1] = grid_limit
      expected_grid[3]["+", label1, 1] = grid_limit
      expected_grid[4]["+", label0, 1] = grid_limit
  
      assert np.isclose(expected_grid.values, grid.values).all()
  
file_path: fairlearn/test/unit/reductions/grid_search/test_grid_generator.py
imports: from test.unit.reductions.grid_search.utilities import _quick_data
  import numpy
  import pandas
  import pytest
  from fairlearn.reductions import DemographicParity, EqualizedOdds
  from fairlearn.reductions._grid_search.grid_search import _GridGenerator
  from fairlearn.reductions._moments.utility_parity import _ALL, _EVENT, _GROUP_ID, _SIGN
label_desc: Use image node_id 3 for calling a global function with example usage: test_grid_generator_equalized_odds_basic(grid_limit) without return types