Bengt Richter wrote: > On 28 Aug 2005 18:54:40 -0700, "[EMAIL PROTECTED]" <[EMAIL PROTECTED]> wrote: > > >Steven Bethard wrote: > >> Adam Tomjack wrote: > >> > Steven Bethard wrote: > >> > ... > >> >> Using a two element list to store a pair of counts has a bad code > >> >> smell to me. > >> > ... > >> > > >> > Why is that? > >> > >> Note that "code smell"[1] doesn't mean that something is actually wrong, > >> just that it might be. In Python, pairs are usually handled with > >> tuples[2], but tuples would be inconvenient in this case, since the > >> first value must be modified. Declaring a class with two attributes as > >> you suggested is often a good substitute, but if the OP's code is really > >> what it looks like, I get another code smell because declaring a class > >> to be used by only 10 lines of code seems like overkill. > >> > >> I also get a code smell from a dict holding two-element lists because > >> I've been writing in Python and answering questions on the Python-list > >> for a couple of years now, and I've never needed one yet. ;-) > >> > >> STeVe > >> > >> [1]http://en.wikipedia.org/wiki/Code_smell > >> [2]http://www.python.org/doc/faq/general.html#why-are-there-separate-tuple-and-list-data-types > > > >Could you do me a favor and see what this smells like? > > > >I put some data in a csv file (with headers) and this will > >bring it in quite simply as a dictionary with [names] as > >keys and an attribute dictionary as the value. > > > >py_monsters.csv: > > > >name,hardiness,agility,friend,courage,room,weight,special_def_odds,armor,weapon,odds,dice,side,hits,reaction,desc > >PIRATE,5,20,0,10,26,300,0,0,11,60,1,10,0,"not met",You see a man with a > >beard and a brass ring in his ear. He is wearing clothes made of silk > >and is wielding a very fancily engraved sword. > > > > > >import csv > >temp1 = [] > >temp2 = [] > >reader = csv.reader(file(r"py_monsters.csv")) > >for rec in reader: > > temp1.append(rec) > >for i in temp1[1:]: > > temp2.append((i[0],dict(zip(temp1[0][1:],i[1:])))) > >monsters = dict(temp2) > > > >This gives me what I want > > > >[('PIRATE', {'reaction': 'not met', > >'agility': '20', > >'room': '26', > >'weight': '300', > >'armor': '0', > >'weapon': '11', > >'hits': '0', > >'side': '10', > >'special_def_odds': '0', > >'courage': '10', > >'hardiness': '5', > >'desc': 'You see a man with a beard and a brass ring in his ear. > >He is wearing clothes made of silk and is wielding a very fancily > >engraved sword.', > >'odds': '60', > >'friend': '0', > >'dice': '1'})] > > > >so that I can now write code like > > > >if monsters['PIRATE']['reaction']=='not met': > > print monsters['PIRATE']['desc'] > > I think if the field names are legal python names, I would rather write that > 'if ...' > without all that line noise ;-) E.g., using simple classes (and effectively > using > their attribute instance dicts essentially the way you used raw dicts), you > could write > > if monsters.PIRATE.reaction == 'not met': > print monsters.PIRATE.desc > > Also, if the reaction, agility, etc list is fixed, you could use __slots__ for > better efficiency. Also, your __init__ method for the latter could convert > strings to ints for handier use later (unless csv already does that in the > mode > you are using).
No, it doesn't as I found out shortly after posting that. What was I thinking? I've got it fixed for the moment, but that idea of classes sounds interesting. > > From the above code I infer that you can do define the requisite classes, so > I'll leave it to you ;-) Guess I'll have to actually start reading the manuals. > Note that attribute access opens the door to having > default values as class variables, and using properties to retrieve > dynamically > calculated values by name. If you are not familiar with those aspects of > classes, > your progammer.agility value can increase markedly with a little study ;-) > > E.g., a name like monsters.random_elf could live right > alongside PIRATE and return one a randomly selected elf from a an internal > list > of elves or via random selection from a list of elf names defined at the same > level as PIRATE, etc. etc. You could also dynamically configure these guys > according to distance to food and time since last meal, and if you are > carrying food, etc. > > With suitable classes you could put instances in various "spaces" defined > by other classes, that define geometric or social or other interactions. Well, this is a port of The Wonderful World of Eamon, which isn't quite that ambitious, but thanks for the idea about classes. It's one of those many things I just skim past without ever understanding. Now would be a good time to start learning it. > > > > >instead of using stupid index numbers. > > > >But the loader seems to have a kind of perl-like odor to it, > >i.e., next week I won't understand what it does. > > > If you have to do something tricky, choose names wisely and > comment the non-obvious ;-) > > Regards, > Bengt Richter -- http://mail.python.org/mailman/listinfo/python-list