docs: def add_data(self, data_id=None, default_value=EMPTY, initial_dist=0.0,
                   wait_inputs=False, wildcard=None, function=None, callback=None,
                   description=None, filters=None, await_result=None, **kwargs):
          """
          Add a single data node to the dispatcher.
  
          :param data_id:
              Data node id. If None will be assigned automatically ('unknown<%d>')
              not in dmap.
          :type data_id: str, optional
  
          :param default_value:
              Data node default value. This will be used as input if it is not
              specified as inputs in the ArciDispatch algorithm.
          :type default_value: T, optional
  
          :param initial_dist:
              Initial distance in the ArciDispatch algorithm when the data node
              default value is used.
          :type initial_dist: float, int, optional
  
          :param wait_inputs:
              If True ArciDispatch algorithm stops on the node until it gets all
              input estimations.
          :type wait_inputs: bool, optional
  
          :param wildcard:
              If True, when the data node is used as input and target in the
              ArciDispatch algorithm, the input value will be used as input for
              the connected functions, but not as output.
          :type wildcard: bool, optional
  
          :param function:
              Data node estimation function.
              This can be any function that takes only one dictionary
              (key=function node id, value=estimation of data node) as input and
              return one value that is the estimation of the data node.
          :type function: callable, optional
  
          :param callback:
              Callback function to be called after node estimation.
              This can be any function that takes only one argument that is the
              data node estimation output. It does not return anything.
          :type callback: callable, optional
  
          :param description:
              Data node's description.
          :type description: str, optional
  
          :param filters:
              A list of functions that are invoked after the invocation of the
              main function.
          :type filters: list[function], optional
  
          :param await_result:
              If True the Dispatcher waits data results before assigning them to
              the solution. If a number is defined this is used as `timeout` for
              `Future.result` method [default: False]. Note this is used when
              asynchronous or parallel execution is enable.
          :type await_result: bool|int|float, optional
  
          :param kwargs:
              Set additional node attributes using key=value.
          :type kwargs: keyword arguments, optional
  
          :return:
              Data node id.
          :rtype: str
  
          .. seealso:: :func:`add_func`, :func:`add_function`,
             :func:`add_dispatcher`, :func:`add_from_lists`
  
          **--------------------------------------------------------------------**
  
          **Example**:
  
          .. testsetup::
              >>> dsp = Dispatcher(name='Dispatcher')
  
          Add a data to be estimated or a possible input data node::
  
              >>> dsp.add_data(data_id='a')
              'a'
  
          Add a data with a default value (i.e., input data node)::
  
              >>> dsp.add_data(data_id='b', default_value=1)
              'b'
  
          Create a data node with function estimation and a default value.
  
              - function estimation: estimate one unique output from multiple
                estimations.
              - default value: is a default estimation.
  
              >>> def min_fun(kwargs):
              ...     '''
              ...     Returns the minimum value of node estimations.
              ...
              ...     :param kwargs:
              ...         Node estimations.
              ...     :type kwargs: dict
              ...
              ...     :return:
              ...         The minimum value of node estimations.
              ...     :rtype: float
              ...     '''
              ...
              ...     return min(kwargs.values())
              ...
              >>> dsp.add_data(data_id='c', default_value=2, wait_inputs=True,
              ...              function=min_fun)
              'c'
  
          Create a data with an unknown id and return the generated id::
  
              >>> dsp.add_data()
              'unknown'
          """
  
          # Set special data nodes.
          if data_id is START:
              default_value, description = NONE, START.__doc__
          elif data_id is SINK:
              wait_inputs, function, description = True, bypass, SINK.__doc__
          elif data_id is SELF:
              default_value, description = self, SELF.__doc__
          elif data_id is PLOT:
              from .utils.drw import autoplot_callback, autoplot_function
              callback, description = callback or autoplot_callback, PLOT.__doc__
              function = function or autoplot_function
  
          # Base data node attributes.
          attr_dict = {
              'type': 'data',
              'wait_inputs': wait_inputs,
              'index': (self.counter(),)
          }
  
          if function is not None:  # Add function as node attribute.
              attr_dict['function'] = function
  
          if await_result is not None:  # Add await_result as node attribute.
              attr_dict['await_result'] = await_result
  
          if callback is not None:  # Add callback as node attribute.
              attr_dict['callback'] = callback
  
          if wildcard is not None:  # Add wildcard as node attribute.
              attr_dict['wildcard'] = wildcard
  
          if description is not None:  # Add description as node attribute.
              attr_dict['description'] = description
  
          if filters:  # Add filters as node attribute.
              attr_dict['filters'] = filters
  
          attr_dict.update(kwargs)  # Additional attributes.
  
          has_node = self.dmap.has_node  # Namespace shortcut for speed.
  
          if data_id is None:  # Search for an unused node id.
              from .utils.alg import get_unused_node_id
              data_id = get_unused_node_id(self.dmap)  # Get an unused node id.
  
          # Check if the node id exists as function.
          elif has_node(data_id) and self.dmap.nodes[data_id]['type'] != 'data':
              raise ValueError('Invalid data id: '
                               'override function {}'.format(data_id))
  
          # Add node to the dispatcher map.
          self.dmap.add_node(data_id, **attr_dict)
  
          # Set default value.
          self.set_default_value(data_id, default_value, initial_dist)
  
          return data_id