code: def walk(self, action, doc=None):
          
  
          # Infer the document thanks to .parent magic
          if doc is None:
              doc = self.doc
  
          # First iterate over children
          for child in self._children:
              obj = getattr(self, child)
              if isinstance(obj, Element):
                  ans = obj.walk(action, doc)
              elif isinstance(obj, ListContainer):
                  ans = (item.walk(action, doc) for item in obj)
                  # We need to convert single elements to iterables, so that they
                  # can be flattened later
                  ans = ((item,) if type(item) != list else item for item in ans)
                  # Flatten the list, by expanding any sublists
                  ans = list(chain.from_iterable(ans))
              elif isinstance(obj, DictContainer):
                  ans = [(k, v.walk(action, doc)) for k, v in obj.items()]
                  ans = [(k, v) for k, v in ans if v != []]
              elif obj is None:
                  ans = None  # Empty table headers or captions
              else:
                  raise TypeError(type(obj))
              setattr(self, child, ans)
  
          # Then apply the action to the element
          altered = action(self, doc)
          return self if altered is None else altered
docs: Walk through the element and all its children (sub-elements),
          applying the provided function ``action``.
  
          A trivial example would be:
  
          .. code-block:: python
  
              from panflute import *
  
              def no_action(elem, doc):
                  pass
  
              doc = Doc(Para(Str('a')))
              altered = doc.walk(no_action)
  
  
          :param action: function that takes (element, doc) as arguments.
          :type action: :class:`function`
          :param doc: root document; used to access metadata,
              the output format (in ``.format``, other elements, and
              other variables). Only use this variable if for some reason
              you don't want to use the current document of an element.
          :type doc: :class:`.Doc`
          :rtype: :class:`Element` | ``[]`` | ``None``