Lisp mentality vs. Python mentality
bearophileHUGS at lycos.com
bearophileHUGS at lycos.com
Sun Apr 26 08:07:25 EDT 2009
Paul Rubin:
> Arnaud Delobelle:
> > Do you mean imap(comp, a, b)?
>
> Oh yes, I forgot you can do that. Thanks.
That works and is nice and readable:
import operator
from itertools import imap
def equal_sequences(a, b, comp=operator.eq):
"""
a and b must have __len__
>>> equal_sequences([1, 2, 3], [1, 2, 3])
True
>>> L1, L2 = [1, 2, 3], [1, -2, 3]
>>> equal_sequences(L1, L2)
False
>>> equal_sequences(L1, L2, lambda x,y: abs(x) == abs(y))
True
>>> L3, L4 = ["hello", "HALLO"], ["hello", "hallo"]
>>> equal_sequences(L3, L4)
False
>>> equal_sequences(L3, L4, lambda x,y: x.lower() == y.lower())
True
"""
return len(a) == len(b) and all(imap(comp, a, b))
if __name__ == "__main__":
import doctest
doctest.testmod()
print "Doctests finished.\n"
But both sequences must have a len. Otherwise you may use (if you
don't have izip_longest the folllowing code gets longer):
"""
>>> equal_items([1, 2], [1, 2, 3])
False
>>> equal_items([1, 2, 3], [1, 2, 3])
True
>>> equal_items([1, 2, 3], [1, -2, 3])
False
>>> equal_items([1, 2, 3], [1, -2, 3], abs)
True
>>> equal_items([1, 2, 3], [1, -2, 4], abs)
False
>>> L1, L2 = ["hello", "HALLO"], ["hello", "hallo"]
>>> equal_items(L1, L2)
False
>>> equal_items(L1, L2, str.lower)
True
>>> equal_items(xrange(3), (i for i in xrange(3)))
True
>>> equal_items([0, 1, 2], (i for i in xrange(3)))
True
>>> equal_items([0, 1, 2, 3], (i for i in xrange(3)))
False
>>> equal_items([-0, -1, -2], (i for i in xrange(3)), key=abs)
True
>>> equal_items([-0, -1, -2, -3], (i for i in xrange(3)), key=abs)
False
>>> x = []
>>> equal_items( (x for i in range(3)), (x for i in range(3)) )
True
>>> equal_items( (x for i in range(3)), (x for i in range(4)) )
False
>>> equal_items( (x for i in range(3)), (x for i in range(3)), key=id)
True
>>> equal_items( (x for i in range(3)), (x for i in range(4)), key=id)
False
>>> equal_items( (x for i in range(3)), (x for i in range(3)), key=lambda x:x)
True
>>> equal_items( (x for i in range(3)), (x for i in range(4)), key=lambda x:x)
False
"""
from itertools import izip_longest
def equal_items(iter1, iter2, key=None):
try:
len_iter1 = len(iter1)
len_iter2 = len(iter2)
except TypeError:
pass
else:
if len_iter1 != len_iter2:
return False
class Guard(object): pass
if key is None:
for x, y in izip_longest(iter1, iter2, fillvalue=Guard()):
if x != y:
return False
else:
try:
for x, y in izip_longest(iter1, iter2, fillvalue=Guard()):
if key(x) != key(y):
return False
except TypeError: # intercepts key(guard)
return False
return True
if __name__ == "__main__":
import doctest
doctest.testmod()
print "Doctests finished.\n"
You can write hairy code in Python too, not just in CLisp :-)
Bye,
bearophile
More information about the Python-list
mailing list