[Tutor] Some sample code: review?

Kent Johnson kent37 at tds.net
Fri Nov 10 12:34:49 CET 2006


Danny Yoo wrote:
> Hi everyone,
> 
> 
> I wrote up some sample code to make a more extensible str()-like function. 
> I'd like some comments before putting it up onto the Python Cookbook:

Hi Danny,

This looks very clean to me. It is surprisingly complex but I don't see 
how to make it simpler.

Some of the names and comments are confusing, I've commented below. 
Other than that it looks good to me.

Kent

> 
> #####################################################################
> class DeepStr:
>      """Deep stringifier."""
>      def __init__(self, default_str=str,
>                         recursive_str=lambda obj, dstr: "..."):
>          """Creates a new DeepStr.  Once constructed, call as if this
>          were a function that takes objects and returns strings.
> 
>          default_str is the default function used on types that this
>          does not recognize.

What are the arguments to default_str? dstr is not a very explanatory 
name, maybe deep_str would be better.
> 
>          If we hit structure that's already been traversed,
>          uses recursive_str to represent that structure."""
>          self.__handlers = []
>          self.__default_str = default_str
>          self.__recursive_str = recursive_str
> 
>      def __call__(self, obj):
>          """Takes a datum and returns a string of that object."""
>          return self.__deepstr(obj, {})
> 
>      def __deepstr(self, obj, _seen):

I would call it 'seen', it isn't an attribute so why the _ ?
>          if id(obj) in _seen:
>              return self.__recursive_str(obj, self)
>          _seen[id(obj)] = True
> 
>          for h in self.__handlers:
>              result = h(obj, lambda o: self.__deepstr(o, _seen))
>              if result != None:
>                  return result
>          return self.__default_str(obj)
> 
>      def register(self, handler):
>          """register: (object (object -> string) -> string or None)

Maybe it's just me but I don't have a clue what 'object (object -> 
string)' is trying to convey.

>             Registers a new handler type.  Handers take in the object
>             as well as a str() function, and returns either a string

maybe call it a deep_str() function, that will make the analogy clearer.

>             if it can handle the object, or None otherwise.  The second
>             argument should be used on substructures."""
>          self.__handlers.append(handler)
> 
> 
> def handle_list(obj, dstr):
>      if isinstance(obj, list):
>          return "[" + ", ".join([dstr(x) for x in obj]) + "]"
>      return None
> 
> def handle_tuple(obj, dstr):
>      if isinstance(obj, tuple):
>          return "(" + ", ".join([dstr(x) for x in obj]) + ")"
>      return None
> 
> def handle_dict(obj, dstr):
>      if isinstance(obj, dict):
>          return ("{" +
>                  ", ".join([dstr(k) + ':' + dstr(v)
>                             for (k, v) in obj.items()]) +
>                  "}")
>      return None
> 
> dstr = DeepStr()
> dstr.register(handle_list)
> dstr.register(handle_tuple)
> dstr.register(handle_dict)
> #####################################################################
> 
> 
> The idea is that Python's str() on lists uses repr() on internal 
> structure, which some people might consider a little wacky.  dstr(), on 
> the other hand, will go all the way deeply through a structure, using the 
> same stringifier.  It's also open for extension so that it can handle 
> different container types in the future.
> 
> Any comments would be greatly appreciated.
> _______________________________________________
> Tutor maillist  -  Tutor at python.org
> http://mail.python.org/mailman/listinfo/tutor
> 
> 




More information about the Tutor mailing list