code: def _ft_create_ei(
      self,
      vi,
      ft_feature,
      dt_unit,
      coldtypedic,
      transfer_features,
      max_pairs,
      verboseprint,
      logfile,
      symmetry,
  ):
      ftf = ft_feature[0]
      ftt = ft_feature[1]
  
      if symmetry == "trapez":
          # dimensions of the trapez
          # nl: number of targets
          # ns: number of sources
          # nd: nl - ns
          if dt_unit is None:
              ns = (vi[ftf] < vi.at[vi.iloc[-1].name, ftf] - ftt).sum()
          else:
              ns = (
                  vi[ftf]
                  < vi.at[vi.iloc[-1].name, ftf]
                  - np.timedelta64(ftt, dt_unit)
              ).sum()
  
          vi = vi.iloc[:-1]
          nl = len(vi)
  
          nd = nl - ns
          # number of pairs
          pairs = (ns * (ns - 1)) // 2 + nd * ns
  
          if nl == 1:
              # for testing
              self._triggered["gap_cases"] += 1
  
              # only happens for "gap" cases
              verboseprint(
                  "# ====================================================="
              )
              verboseprint(" nr of pairs: [{}]".format(pairs))
              ei = pd.DataFrame(
                  {
                      col: pd.Series(data=[], dtype=dtype)
                      for col, dtype in coldtypedic.items()
                  }
              )
  
              return [ei], ns
  
          else:
              if pairs > max_pairs:
                  verboseprint(
                      "# ====================================================="
                  )
                  verboseprint("maximum number of pairs exceeded")
                  verboseprint(" nr of pairs: [{}]".format(pairs))
                  ei = _ft_subiterator(
                      nl,
                      vi,
                      ft_feature,
                      dt_unit,
                      coldtypedic,
                      transfer_features,
                      pairs,
                      max_pairs,
                      verboseprint,
                  )
                  # logging
                  if logfile:
                      with open(logfile, "a") as log:
                          print(
                              "1\t{}\t".format(pairs), end="", file=log
                          )
  
                  return ei, ns
  
              else:
                  # construct node indices
                  sources, targets = _triu_indices(nl, 0, pairs)
  
                  verboseprint(
                      "# ====================================================="
                  )
                  verboseprint(" nr of pairs: [{}]".format(pairs))
                  ei = _select_and_return(
                      vi,
                      sources,
                      targets,
                      ft_feature,
                      dt_unit,
                      transfer_features,
                      coldtypedic,
                  )
                  # logging
                  if logfile:
                      with open(logfile, "a") as log:
                          print(
                              "0\t{}\t".format(len(sources)),
                              end="",
                              file=log,
                          )
  
                  return [ei], ns
  
      elif symmetry == "triangle":
          # dimensions of the square
          # nl: number of targets
          # ns: number of sources
          # nd: nl - ns = 0
          nl = len(vi)
          ns = len(vi)
          nd = 0
  
          # number of pairs
          pairs = (nl * (nl - 1)) // 2
  
          if pairs > max_pairs:
              verboseprint(
                  "# ====================================================="
              )
              verboseprint("maximum number of pairs exceeded")
              verboseprint(" nr of pairs: [{}]".format(pairs))
              ei = _ft_subiterator(
                  nl,
                  vi,
                  ft_feature,
                  dt_unit,
                  coldtypedic,
                  transfer_features,
                  pairs,
                  max_pairs,
                  verboseprint,
              )
              # logging
              if logfile:
                  with open(logfile, "a") as log:
                      print("1\t{}\t".format(pairs), end="", file=log)
  
              return ei, ns
  
          else:
              # construct node indices
              sources, targets = np.triu_indices(nl, k=1)
              sources = sources.astype(np.uint64)
              targets = targets.astype(np.uint64)
  
              verboseprint(
                  "# ====================================================="
              )
              verboseprint(" nr of pairs: [{}]".format(pairs))
              ei = _select_and_return(
                  vi,
                  sources,
                  targets,
                  ft_feature,
                  dt_unit,
                  transfer_features,
                  coldtypedic,
              )
              # logging
              if logfile:
                  with open(logfile, "a") as log:
                      print(
                          "0\t{}\t".format(len(sources)),
                          end="",
                          file=log,
                      )
  
              return [ei], ns
  
file_path: deepgraph/deepgraph/iterators_and_indexers.py
imports: from datetime import datetime
  from itertools import chain
  import numpy
  import pandas
  from deepgraph._triu_indices import _triu_indices, _union_of_indices, _reduce_triu_indices
  from deepgraph.connector_selector_implementations import _ft_connector, _ft_selector
  from deepgraph.connectors_and_selectors import CreatorFunction, Selector, Connector
  from deepgraph.utils import _flatten, _is_array_like, _merge_dicts
label_desc: Use image node_id 8 for calling a global function with example usage: _ft_create_ei(vi, ft_feature, dt_unit, coldtypedic, transfer_features, max_pairs, verboseprint, logfile, symmetry) and returns: list,  ns, ei,  ns, list,  ns, ei,  ns, list,  ns