code: def mutNodeReplacement(individual, pset):
      """Replaces a randomly chosen primitive from *individual* by a randomly
      chosen primitive no matter if it has the same number of arguments from the :attr:`pset`
      attribute of the individual.
      Parameters
      ----------
      individual: DEAP individual
          A list of pipeline operators and model parameters that can be
          compiled by DEAP into a callable function
  
      Returns
      -------
      individual: DEAP individual
          Returns the individual with one of point mutation applied to it
  
      """
  
      index = np.random.randint(0, len(individual))
      node = individual[index]
      slice_ = individual.searchSubtree(index)
  
      if node.arity == 0:  # Terminal
          term = np.random.choice(pset.terminals[node.ret])
          if isclass(term):
              term = term()
          individual[index] = term
      else:  # Primitive
          # find next primitive if any
          rindex = None
          if index + 1 < len(individual):
              for i, tmpnode in enumerate(
                  individual[index + 1 :], index + 1
              ):
                  if (
                      isinstance(tmpnode, gp.Primitive)
                      and tmpnode.ret in node.args
                  ):
                      rindex = i
                      break
  
          # pset.primitives[node.ret] can get a list of the type of node
          # for example: if op.root is True then the node.ret is Output_DF object
          # based on the function _setup_pset. Then primitives is the list of classifor or regressor
          primitives = pset.primitives[node.ret]
  
          if len(primitives) != 0:
              new_node = np.random.choice(primitives)
              new_subtree = [None] * len(new_node.args)
              if rindex:
                  rnode = individual[rindex]
                  rslice = individual.searchSubtree(rindex)
                  # find position for passing return values to next operator
                  position = np.random.choice(
                      [
                          i
                          for i, a in enumerate(new_node.args)
                          if a == rnode.ret
                      ]
                  )
              else:
                  position = None
              for i, arg_type in enumerate(new_node.args):
                  if i != position:
                      term = np.random.choice(pset.terminals[arg_type])
                      if isclass(term):
                          term = term()
                      new_subtree[i] = term
              # paste the subtree to new node
              if rindex:
                  new_subtree[position : position + 1] = individual[
                      rslice
                  ]
              # combine with primitives
              new_subtree.insert(0, new_node)
              individual[slice_] = new_subtree
  
      return (individual,)
  
file_path: tpot/tpot/gp_deap.py
imports: import numpy
  from deap import tools, gp
  from inspect import isclass
  from .operator_utils import set_sample_weight
  from sklearn.utils import indexable
  from sklearn.metrics import check_scoring
  from sklearn.model_selection._validation import _fit_and_score
  from sklearn.base import clone
  from collections import defaultdict
  import warnings
  from stopit import threading_timeoutable, TimeoutException
label_desc: Use image node_id 7 for calling a global function with example usage: mutNodeReplacement(individual, pset) and returns: individual