Taking a step back a bit... the basic issue is that we have an attribute 
namespace (compile time key determination) that we want to access in a 
dictionary style (runtime key determination).

This is currently done by switching from syntactic access to the 
getattr/setattr/delattr builtin functions.

Elsewhere in the thread, Calvin made the suggestion that, rather than 
introducing new syntax, this could instead be achieved with a wrapper 
class that automatically converted dict-style access into the 
appropriate calls to getattr/setattr/delattr.

I've tried this out on Brett's urllib & urllib2 examples below. (calling 
the new builtin attrview() to emphasise the fact that it retains a 
reference to the original instance). I don't consider it any uglier than 
the proposed syntax changes, and it provides a few other benefits:

   - the two-argument form is naturally available as the .get() method 
on the resulting dict-like object (e.g. "attrview(obj).get(some_attr, 
None)")

   - hasattr() is naturally replaced by containment testing (e.g. 
"some_attr in attrview(obj)")

   - keywords/builtins are easier to look up in the documentation than 
symbolic syntax

With this approach, performance would be attained by arranging to create 
the view objects once, and then performing multiple dynamic attribute 
accesses using those view objects.

First urllib.py example::

     name = 'open_' + urltype
     self.type = urltype
     name = name.replace('-', '_')
     self_d = attrview(self)
     if name in self_d:
         if proxy:
             return self.open_unknown_proxy(proxy, fullurl, data)
         else:
             return self.open_unknown(fullurl, data)
     try:
         if data is None:
             return self_d[name](url)
         else:
             return self_d[name](url, data)
     except socket.error, msg:
         raise IOError, ('socket error', msg), sys.exc_info()[2]

Second urllib.py example::

     name = 'http_error_%d' % errcode
     self_d = attrview(self)
     if name in self_d:
         method = self_d[name]
         if data is None:
             result = method(url, fp, errcode, errmsg, headers)
         else:
             result = method(url, fp, errcode, errmsg, headers, data)
         if result: return result
     return self.http_error_default(url, fp, errcode, errmsg, headers)


First urllib.py example::

         if attr[:12] == '_Request__r_':
             name = attr[12:]
             get_name = 'get_' + name
             if get_name in attrview(Request):
                 self_d = attrview(self)
                 self_d[get_name]()
                 return self_d[attr]
         raise AttributeError, attr

Second urllib2.py example::

         handlers = chain.get(kind, ())
         for handler in handlers:
             func = attrview(handler)[meth_name]
             result = func(*args)
             if result is not None:
                 return result

Regards,
Nick.

-- 
Nick Coghlan   |   [EMAIL PROTECTED]   |   Brisbane, Australia
---------------------------------------------------------------
             http://www.boredomandlaziness.org
_______________________________________________
Python-Dev mailing list
Python-Dev@python.org
http://mail.python.org/mailman/listinfo/python-dev
Unsubscribe: 
http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com

Reply via email to