docs: def key_map(f, m, *args, **kwargs):
      '''
      key_map(f, m) is equivalent to {f(k):v for (k,v) in m.items()} except that it returns a
        persistent mapping object instead of a dict. Additionally, it respects the laziness of maps
        and does not evaluate the values of a lazy map that has been passed to it.
      key_map(f, m, *args, **kwargs) uses f(k, *args, **kwargs) instead of f(k).
      '''
      if is_lazy_map(m):
          from .table import (is_itable, itable)
          def _curry_getval(k): return lambda:m[k]
          m0 = {f(k, *args, **kwargs):_curry_getval(k) for k in six.iterkeys(m)}
          return itable(m0) if is_itable(m) else lazy_map(m0)
      else:
          return ps.pmap({f(k, *args, **kwargs):v for (k,v) in six.iteritems(m)})