我想解析文件中的数据,并且我想要验证每一行数据。想象一下,文件的前几行看起来像这样:
id|date|rate|notes
1|2016-07-23|0.765|foo
2|2016-07-23|0.432|
1|2016-07-24|0.697|bar
我想确保date
和rate
值有效,并且我有可以检查它们的函数。如果输入有效,这些函数返回一个值,如果输入有效则返回错误。 E.g:
def validate_date(string):
parts = [int(x) for x in string.split("-")
return datetime.date(*parts)
我不关心id
或notes
字段的值。所以我可以这样做:
validators = dict()
validators['id'] = lambda x: x
validators['date'] = validate_date
validators['rate'] = validate_rate
validators['notes'] = lambda x: x
然后,一旦我读完每一行(作为字典),我就可以像这样验证每个字段:
output = dict()
for key, value in line.iteritems()
output[key] = validators[key](value)
return output
这一切都很棒。问题是我要解析的文件实际上有几十个我不关心的字段,而且我只做了一些。因此,我不想手动定义像validators['id'] = lambda x: x
这样的行,而是使用像defaultdict
之类的东西来返回一个只返回输入的函数。但是,如果我尝试:
def do_nothing(x):
return x
foo = defaultdict(do_nothing)
foo['bar'](1)
我收到错误:do_nothing() takes exactly 1 argument (0 given)
。
有没有办法创建类似defaultdict
的东西,但会返回一个可以参数的对象?
答案 0 :(得分:3)
defaultdict
返回由其默认函数创建的内容,因此您只需要do_nothing
返回一个需要一个参数的可调用对象。您根本不需要do_nothing
,只需
validators = collections.defaultdict(lambda: lambda x: x)
现在defaultdict
会返回lambda x: x
,其中包含一个参数,因此您可以执行
validators['foo'](1)
并使用1
调用lambda。