开发者

Chaining operator functions in Python's filter

I have a list of objects and want to filter them according to some criteria. I can do it with list comprehension:

import datetime, pytz
# let's have a range of 100 hourly datetimes (just an example!):
dates = [ datetime.datetime(2010, 10, 1, 0, 0, 0, 0, pytz.utc) + datetime.timedelta(hours=i) for i in xrange(100) ]

# now I want a list of all dates, where hour in (0, 6, 12, 18)...
[ dt for dt in dates if dt.hour % 6 == 0 ]

Which works correctly.

How can I use the filter function (for much larger datasets, t开发者_高级运维herefore the speed is important)? I can check whether dt.hour is True (not 0):

import operator

filter(operator.attrrgetter('hour'), dates)

but how can I put also the (6).__rmod__ part to it, which will tell me whether the hour attribute is divisible by 6?


One way is to use a custom lambda function. This one is verbose for clarity.

filter(lambda dt: hasattr(dt, 'hour') and dt.hour % 6, dates)

The hasattr check is only necessary if you are expecting non date objects in the dates sequence.

I'd like to add a note that list comprehensions are preferred to map and filter. You could rewrite the above as:

[dt for dt in dates if hasattr(dt, 'hour') and dt.hour % 6]


Unfortunately there's no prefab method for doing rmod, so best is to use a lambda (or a LC).

filter(lambda x: not x.hour % 6, dates)
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜