code: def test_merge(setup):
      df1 = pd.DataFrame(
          np.arange(20).reshape((4, 5)) + 1,
          columns=["a", "b", "c", "d", "e"],
      )
      df2 = pd.DataFrame(
          np.arange(20).reshape((5, 4)) + 1,
          columns=["a", "b", "x", "y"],
      )
      df3 = df1.copy()
      df3.index = pd.RangeIndex(2, 6, name="index")
      df4 = df1.copy()
      df4.index = pd.MultiIndex.from_tuples(
          [(i, i + 1) for i in range(4)], names=["i1", "i2"]
      )
  
      mdf1 = from_pandas(df1, chunk_size=2)
      mdf2 = from_pandas(df2, chunk_size=2)
      mdf3 = from_pandas(df3, chunk_size=3)
      mdf4 = from_pandas(df4, chunk_size=2)
  
      # Note [Index of Merge]
      #
      # When `left_index` and `right_index` of `merge` is both false, pandas will generate an RangeIndex to
      # the final result dataframe.
      #
      # We chunked the `left` and `right` dataframe, thus every result chunk will have its own RangeIndex.
      # When they are contenated we don't generate a new RangeIndex for the result, thus we cannot obtain the
      # same index value with pandas. But we guarantee that the content of dataframe is correct.
  
      # merge on index
      expected0 = df1.merge(df2)
      jdf0 = mdf1.merge(mdf2, auto_merge="none")
      result0 = jdf0.execute().fetch()
      pd.testing.assert_frame_equal(
          sort_dataframe_inplace(expected0, 0),
          sort_dataframe_inplace(result0, 0),
      )
  
      # merge on left index and `right_on`
      expected1 = df1.merge(
          df2, how="left", right_on="x", left_index=True
      )
      jdf1 = mdf1.merge(
          mdf2,
          how="left",
          right_on="x",
          left_index=True,
          auto_merge="none",
      )
      result1 = jdf1.execute().fetch()
      expected1.set_index("a_x", inplace=True)
      result1.set_index("a_x", inplace=True)
      pd.testing.assert_frame_equal(
          sort_dataframe_inplace(expected1, 0),
          sort_dataframe_inplace(result1, 0),
      )
  
      # merge on `left_on` and right index
      expected2 = df1.merge(
          df2, how="right", left_on="a", right_index=True
      )
      jdf2 = mdf1.merge(
          mdf2,
          how="right",
          left_on="a",
          right_index=True,
          auto_merge="none",
      )
      result2 = jdf2.execute().fetch()
      expected2.set_index("a", inplace=True)
      result2.set_index("a", inplace=True)
      pd.testing.assert_frame_equal(
          sort_dataframe_inplace(expected2, 0),
          sort_dataframe_inplace(result2, 0),
      )
  
      # merge on `left_on` and `right_on`
      expected3 = df1.merge(df2, how="left", left_on="a", right_on="x")
      jdf3 = mdf1.merge(
          mdf2, how="left", left_on="a", right_on="x", auto_merge="none"
      )
      result3 = jdf3.execute().fetch()
      expected3.set_index("a_x", inplace=True)
      result3.set_index("a_x", inplace=True)
      pd.testing.assert_frame_equal(
          sort_dataframe_inplace(expected3, 0),
          sort_dataframe_inplace(result3, 0),
      )
  
      # merge on `on`
      expected4 = df1.merge(df2, how="right", on="a")
      jdf4 = mdf1.merge(mdf2, how="right", on="a", auto_merge="none")
      result4 = jdf4.execute().fetch()
      expected4.set_index("a", inplace=True)
      result4.set_index("a", inplace=True)
      pd.testing.assert_frame_equal(
          sort_dataframe_inplace(expected4, 0),
          sort_dataframe_inplace(result4, 0),
      )
  
      # merge on multiple columns
      expected5 = df1.merge(df2, how="inner", on=["a", "b"])
      jdf5 = mdf1.merge(
          mdf2, how="inner", on=["a", "b"], auto_merge="none"
      )
      result5 = jdf5.execute().fetch()
      pd.testing.assert_frame_equal(
          sort_dataframe_inplace(expected5, 0),
          sort_dataframe_inplace(result5, 0),
      )
  
      # merge when some on is index
      expected6 = df3.merge(
          df2, how="inner", left_on="index", right_on="a"
      )
      jdf6 = mdf3.merge(
          mdf2,
          how="inner",
          left_on="index",
          right_on="a",
          auto_merge="none",
      )
      result6 = jdf6.execute().fetch()
      pd.testing.assert_frame_equal(
          sort_dataframe_inplace(expected6, 0),
          sort_dataframe_inplace(result6, 0),
      )
  
      # merge when on is in MultiIndex
      expected7 = df4.merge(
          df2, how="inner", left_on="i1", right_on="a"
      )
      jdf7 = mdf4.merge(
          mdf2,
          how="inner",
          left_on="i1",
          right_on="a",
          auto_merge="none",
      )
      result7 = jdf7.execute().fetch()
      pd.testing.assert_frame_equal(
          sort_dataframe_inplace(expected7, 0),
          sort_dataframe_inplace(result7, 0),
      )
  
      mdf5 = from_pandas(df2, chunk_size=4)
      mdf6 = from_pandas(df4, chunk_size=1)
      expected7 = df4.merge(
          df2, how="inner", left_on="i1", right_on="a"
      )
      jdf7 = mdf6.merge(
          mdf5,
          how="inner",
          left_on="i1",
          right_on="a",
          auto_merge="none",
      )
      result7 = jdf7.execute().fetch()
      pd.testing.assert_frame_equal(
          sort_dataframe_inplace(expected7, 0),
          sort_dataframe_inplace(result7, 0),
      )
  
      # merge when on is in MultiIndex, and on not in index
      expected8 = df4.merge(df2, how="inner", on=["a", "b"])
      jdf8 = mdf4.merge(
          mdf2, how="inner", on=["a", "b"], auto_merge="none"
      )
      result8 = jdf8.execute().fetch()
      pd.testing.assert_frame_equal(
          sort_dataframe_inplace(expected8, 0),
          sort_dataframe_inplace(result8, 0),
      )
  
file_path: mars/mars/dataframe/merge/tests/test_merge_execution.py
imports: import numpy
  import pandas
  import pytest
  from ....core.graph.builder.utils import build_graph
  from ...datasource.dataframe import from_pandas
  from ...datasource.series import from_pandas
  from ...utils import sort_dataframe_inplace
  from ..None import concat, DataFrameConcat, DataFrameMergeAlign
label_desc: Use image node_id 1 for calling a global function with example usage: test_merge(setup) without return types