typechecks: just say no! (was Re: Determining Types)

David C. Ullrich ullrich at math.okstate.edu
Tue Sep 4 16:25:54 CEST 2001

On Mon, 3 Sep 2001 17:22:13 +0200, "Alex Martelli" <aleax at aleax.it>

>"David C. Ullrich" <ullrich at math.okstate.edu> wrote in message
>news:3b938f31.2123170 at nntp.sprynet.com...
>    ...
>> But in other places it's good to be able to refer to
>> fields with non-literal names, so I add a __getitem__
>> so that rec['thisfield'] returns rec.thisfield.
>    ...
>> In yet other places I want to iterate over the fields
>> of a record, as in
>> for key, value in rec:
>> So in __getitem__ I check the type of index, returning
>> getattr(self, index) if index is a string and saying
>> fieldname=self.__fieldnames__[index]
>> return (fieldname, getattr(self, fieldname))
>> if index is an integer.
>> Seems utterly keen to be able to use them as both
>> lists and as mappings, as needed.
>Matter of taste (I personally don't much like any
>confusion between attributes and items), and in Python
>2.2 a far better solution is provided (the for statement
>will first attempt to use the __iter__ method -- just
>implement *that* one to return the iterator you want,

Yes, that would be better.

>and note that for a built-in dictionary
>    for x in dict
>only iterates on KEYS, *not* key-value pairs, so,
>take care to avoid any confusion...).  Admittedly,
>being able to index a Collection on EITHER item
>name or item number IS a typical Visual Basic
>feechur, but that still doesn't much recommend it
>to my personal taste. 

But you should smile when you say this. It's actually
Python idioms I want here. Thought about it and
decided that _explicit_ indexing on _either_ strings
or integers is not going to come up, the only reason
I want them both is so I can say "for key, value in rec"
and also "'a string' % aRec".

> Anyway...:
>If I had to implement this in Python 2.1 or earlier,
>I'd use either variant of "it's easier to get
>forgiveness than permission", which after all IS
>the typical idiom to use where the unenlightened
>would typetest: i.e., either:
>def __getitem__(self, index):
>    try: return getattr(self, index)
>    except AttributeError:
>        fieldname=self.__fieldnames[index]
>        return fieldname, getattr(self, fieldname)

Otoh this is of course the right thing to do,
much better than the explicit type check. Duh.

>def __getitem__(self, index):
>    try:
>        fieldname=self.__fieldnames[index]
>    except TypeError:
>        return getattr(self, index)
>    else:
>        return fieldname, getattr(self, fieldname)
>This would let client-code use any "index" that is
>string'ish enough to please getattr, or int'ish
>enough to please the [] indexing on __fieldnames
>(don't use double leading AND trailing __ for your
>own purposes, they're all "reserved to Python"!-).

A question about that: Is there a _guarantee_ somewhere
that builtin attributes common to all objects always
will have those underscores? (One wants to know that
fieldnames in the database will not conflict with
builtin field names - I imagine that this sort of
consideration is part of where the double underscores
came from in the first place...)


David C. Ullrich

More information about the Python-list mailing list