why UnboundLocalError?

Bengt Richter bokr at oz.net
Sat Jul 9 18:56:26 CEST 2005

On Sat, 09 Jul 2005 06:17:20 GMT, bokr at oz.net (Bengt Richter) wrote:

>On Fri, 8 Jul 2005 21:21:36 -0500, Alex Gittens <swiftset at gmail.com> wrote:
>>I'm trying to define a function that prints fields of given widths
>>with specified alignments; to do so, I wrote some helper functions
>>nested inside of the print function itself. I'm getting an
>>UnboundLocalError, and after reading the Naming and binding section in
>>the Python docs, I don't see why.
>It's not clear what you are trying to do with a field string that's
>wider than the specified width. Do you want to keep printing lines that
>have all blank fields except for where there is left-over too-wide remnants? E.g.,
>if the fields were ['left','left12345','right','12345right'] and the widths were [5,5,6,6] and align 'llrr'
>should the printout be (first two lines below just for ruler reference)
> 1234512345123456123456
> left left1 right12345r
>      2345         ight
>or what? I think you can get the above with more concise code :-)
>but a minor mod to yours seems to do it:

Not very tested, but you may enjoy puzzling out a more concise version
(and writing a proper test for it, since it might have bugs ;-)

 >>> def fieldprint(widths, align, fields):
 ...     if len(widths) != len(fields) or len(widths)!=len(align):
 ...         raise ValueError, 'fieldprint argument mismatch'
 ...     align = [getattr(str, j+'just') for j in align]
 ...     results = []
 ...     while ''.join(fields):
 ...         for i, (fld, wid, alg) in enumerate(zip(fields, widths, align)):
 ...             results.append(alg(fld[:wid], wid))
 ...             fields[i] = fld[wid:]
 ...         results.append('\n')
 ...     return ''.join(results)
 >>> print fieldprint([5,5,6,6], 'llrr', ['left', 'left12345', 'right', '12345right'])
 left left1 right12345r
      2345         ight

BTW, since this destroys the fields list, you might want to operate on a copy
(e.g., remaining_fields = fields[:]) internally, or pass a copy to the routine.
Of course, you could put "print" instead of "return" in fieldprint and just call it
instead of printing what it returns as above, but you didn't show that part in your
original example. BTW2, note that "str" above is the built in string type, and it's
not a good idea to use a built in name for a variable the way your original code did.

Bengt Richter

More information about the Python-list mailing list