dictionary comparison

Bill Mill bill.mill at gmail.com
Thu May 5 12:15:12 EDT 2005


On 5 May 2005 08:19:31 -0700, rickle <devrick88 at gmail.com> wrote:
> I'm trying to compare sun patch levels on a server to those of what sun
> is recommending.  For those that aren't familiar with sun patch
> numbering here is a quick run down.
> 
> A patch number shows up like this:
> 113680-03
> ^^^^^^ ^^
> patch#  revision
> 
> What I want to do is make a list.  I want to show what server x has
> versus what sun recommends, and if the patch exists, but the revision
> is different, I want to show that difference.
> 
> Here are some sample patches that sun recommends:
> 117000-05
> 116272-03
> 116276-01
> 116278-01
> 116378-02
> 116455-01
> 116602-01
> 116606-01
> 
> Here are some sample patches that server x has:
> 117000-01
> 116272-02
> 116272-01
> 116602-02
> 
> So there are some that are the same, some that sun recommends that
> server x doesn't have, and some where the patch is the same but the
> revision is different.
> 
> I've thrown the data into dictionaries, but I just can't seem to figure
> out how I should actually compare the data and present it.  Here's what
> I have so far (the split is in place because there is actually a lot
> more data in the file, so I split it out so I just get the patch number
> and revision).  So I end up with (for example) 116272-01, then split so
> field[0] is 116272 and field[1] is 01.
> 
> def sun():
>         sun = open('sun-patchlist', 'r')
>         for s in sun:
>                 sun_fields = s.split(None, 7)
>                 for sun_field in sun_fields:
>                         sun_field = sun_field.strip()
>                 sun_patch = {}
>                 sun_patch['number'] = sun_fields[0]
>                 sun_patch['rev'] = sun_fields[1]
>                 print sun_patch['number'], sun_patch['rev']
>         sun.close()
> 
> def serverx():
>         serverx = open('serverx-patchlist', 'r')
>         for p in serverx:
>                 serverx_fields = p.split(None, 7)
>                 for serverx_field in serverx_fields:
>                         serverx_field = serverx_field.strip()
>                 serverx_patch = {}
>                 serverx_patch['number'] = serverx_fields[0]
>                 serverx_patch['rev'] = serverx_fields[1]
>                 print serverx_patch['number'], serverx_patch['rev']
>         serverx.close()
> 

The first thing you should notice about this code is that you copied a
good amount of code between functions; this should be a huge warning
bell that something can be abstracted out into a function. In this
case, it's the parsing of the patch files.

Also, you should see that you're creating a new dictionary every
iteration through the loop, and furthermore, you're not returning it
at the end of your function. Thus, it's destroyed when the function
exits and it goes out of scope.

<snip>

Anyway, since you at least made an effort, here's some totally
untested code that should (I think) do something close to what you're
looking for:

def parse_patch_file(f):
    patches = {}
    for line in f:
        patch, rev = line.strip().split('-')
        patches[patch] = rev
    return patches

def diff_patches(sun, serverx):
    for patch in sun:
        if not serverx.has_key(patch):
            print "Sun recommends patch %s" % patch
    for patch in serverx:
        if not sun.has_key(patch):
            print "Serverx has unnecessary patch %s" % patch

def diff_revs(sun, serverx):
    for patch, rev in sun.iteritems():
        if serverx.has_key(patch) and rev != serverx[patch]:
            print "Sun recommends rev %d of patch %s; serverx has rev %d"\
                % (rev, patch, serverx[patch])

if __name__ == '__main__':
    sun = parse_patch_file(open('sun-patchlist'))
    serverx = parse_patch_file(open('serverx-patchlist'))
    diff_patches(sun, serverx)
    diff_revs(sun, serverx)

Hope this helps.

Peace
Bill Mill
bill.mill at gmail.com



More information about the Python-list mailing list