docs: def state_counts(self, variable, parents=[], complete_samples_only=None):
          """
          Return counts how often each state of 'variable' occured in the data.
          If a list of parents is provided, counting is done conditionally
          for each state configuration of the parents.
  
          Parameters
          ----------
          variable: string
              Name of the variable for which the state count is to be done.
  
          parents: list
              Optional list of variable parents, if conditional counting is desired.
              Order of parents in list is reflected in the returned DataFrame
  
          complete_samples_only: bool
              Specifies how to deal with missing data, if present. If set to `True` all rows
              that contain `np.NaN` somewhere are ignored. If `False` then
              every row where neither the variable nor its parents are `np.NaN` is used.
              Desired default behavior can be passed to the class constructor.
  
          Returns
          -------
          state_counts: pandas.DataFrame
              Table with state counts for 'variable'
  
          Examples
          --------
          >>> import pandas as pd
          >>> from pgmpy.estimators import BaseEstimator
          >>> data = pd.DataFrame(data={'A': ['a1', 'a1', 'a2'],
                                        'B': ['b1', 'b2', 'b1'],
                                        'C': ['c1', 'c1', 'c2']})
          >>> estimator = BaseEstimator(data)
          >>> estimator.state_counts('A')
              A
          a1  2
          a2  1
          >>> estimator.state_counts('C', parents=['A', 'B'])
          A  a1      a2
          B  b1  b2  b1  b2
          C
          c1  1   1   0   0
          c2  0   0   1   0
          >>> estimator.state_counts('C', parents=['A'])
          A    a1   a2
          C
          c1  2.0  0.0
          c2  0.0  1.0
          """
          parents = list(parents)
  
          # default for how to deal with missing data can be set in class constructor
          if complete_samples_only is None:
              complete_samples_only = self.complete_samples_only
          # ignores either any row containing NaN, or only those where the variable or its parents is NaN
          data = self.data.dropna() if complete_samples_only else self.data.dropna(subset=[variable] + parents)
  
          if not parents:
              # count how often each state of 'variable' occured
              state_count_data = data.ix[:, variable].value_counts()
              state_counts = state_count_data.reindex(self.state_names[variable]).fillna(0).to_frame()
  
          else:
              parents_states = [self.state_names[parent] for parent in parents]
              # count how often each state of 'variable' occured, conditional on parents' states
              state_count_data = data.groupby([variable] + parents).size().unstack(parents)
              if not isinstance(state_count_data.columns, pd.MultiIndex):
                  state_count_data.columns = pd.MultiIndex.from_arrays([state_count_data.columns])
  
              # reindex rows & columns to sort them and to add missing ones
              # missing row    = some state of 'variable' did not occur in data
              # missing column = some state configuration of current 'variable's parents
              #                  did not occur in data
              row_index = self.state_names[variable]
              column_index = pd.MultiIndex.from_product(parents_states, names=parents)
              state_counts = state_count_data.reindex(index=row_index, columns=column_index).fillna(0)
  
          return state_counts