如何使用字典调用 Python 方法
How to invoke Python methods using a dictionary
我正在尝试创建转换数据的方法列表(或字典)。例如,我有如下数据:
data = [
{'Result': 1, 'Reason1': False, 'Reason2': 1},
{'Result': 0, 'Reason1': False, 'Reason2':'haha'},
{'Result': 0, 'Reason1': True, 'Reason2': 'hehe'},
{'Result': 0, 'Reason1': True, 'Reason2': 0},
]
def rule_1(datum):
modified_datum = datum
if datum['Reason1']:
modified_datum['Result'] = 1 # always set 'Result' to 1 whenever 'Reason1' is True
else:
modified_datum['Result'] = 1 # always set 'Result' to 0 whenever 'Reason1' is False
return modified_datum
def rule_2(datum):
modified_datum = datum
if type(datum['Reason2']) is str:
modified_datum['Result'] = 1 # always set 'Result' to 1 whenever 'Reason2' is of type 'str'
elif type(datum['Reason2']) is int:
modified_datum['Result'] = 2 # always set 'Result' to 2 whenever 'Reason2' is of type 'int'
else:
modified_datum['Result'] = 0
return modified_datum
# There can be 'rule_3', 'rule_4' and so on... Also, these rules may have different method signatures (that is, they may take in more than one input parameter)
rule_book = [rule_2, rule_1] # I want to apply rule_2 first and then rule_1
processed_data = []
for datum in data:
for rule in rule_book:
# Like someone mentioned here, the line below works, but what if I want to have different number of input parameters for rule_3, rule_4 etc.?
# processed_data.append(rule(datum))
我认为 Stack Overflow 上的 this answer 与我正在尝试做的非常接近,但我想向 Python 有经验的人学习如何最好地处理它。我用 'dispatch' 标记了这个 post,我认为这是我想要实现的目标的术语(?)在此先感谢您的帮助和建议!
如评论所述,您非常接近。您需要做的就是在遍历时调用 rule
。
关于处理不同长度的参数,您可以选择在规则中使用 *args
和 **kwargs
。这是一个简单的例子:
def rule1(*args, **kwargs):
# Handling of non-keyword params passed in, if any
if args:
for arg in args:
print(f'{arg} is type {type(arg)}')
# if kwargs is not necessary if you don't intend to handle keyword params
def rule2(*args, **kwargs):
# if args is not necessary if you don't intend to handle non-keyword params
# handling of keyword params passed in, if any
if kwargs:
for k, v in kwargs.items():
print(f'Keyword arg {k} has value {v}')
rule_book = [rule2, rule1]
for rule in rule_book:
# iterate through the rule_book with the same amount of args and kwargs
rule('I am a string', 123, ('This', 'is', 'Tuple'), my_list=[0, 1, 2], my_dict={'A': 0, 'B': 1})
结果:
Keyword arg my_list has value [0, 1, 2]
Keyword arg my_dict has value {'A': 0, 'B': 1}
I am a string is type <class 'str'>
123 is type <class 'int'>
('This', 'is', 'Tuple') is type <class 'tuple'>
关键是要保持规则之间的参数一致,一旦传入所有内容,只需获取相关对象并使用它:
def rule3(*args, **kwargs):
if args:
for arg in args:
if isinstance(arg, tuple):
# if there's a tuple presented, reverse each of the inner items
print([a[::-1] for a in arg])
# ['sihT', 'si', 'elpuT']
根据您构建代码的方式,我相信您应该能够理解并将其应用到您自己的代码中。
我正在尝试创建转换数据的方法列表(或字典)。例如,我有如下数据:
data = [
{'Result': 1, 'Reason1': False, 'Reason2': 1},
{'Result': 0, 'Reason1': False, 'Reason2':'haha'},
{'Result': 0, 'Reason1': True, 'Reason2': 'hehe'},
{'Result': 0, 'Reason1': True, 'Reason2': 0},
]
def rule_1(datum):
modified_datum = datum
if datum['Reason1']:
modified_datum['Result'] = 1 # always set 'Result' to 1 whenever 'Reason1' is True
else:
modified_datum['Result'] = 1 # always set 'Result' to 0 whenever 'Reason1' is False
return modified_datum
def rule_2(datum):
modified_datum = datum
if type(datum['Reason2']) is str:
modified_datum['Result'] = 1 # always set 'Result' to 1 whenever 'Reason2' is of type 'str'
elif type(datum['Reason2']) is int:
modified_datum['Result'] = 2 # always set 'Result' to 2 whenever 'Reason2' is of type 'int'
else:
modified_datum['Result'] = 0
return modified_datum
# There can be 'rule_3', 'rule_4' and so on... Also, these rules may have different method signatures (that is, they may take in more than one input parameter)
rule_book = [rule_2, rule_1] # I want to apply rule_2 first and then rule_1
processed_data = []
for datum in data:
for rule in rule_book:
# Like someone mentioned here, the line below works, but what if I want to have different number of input parameters for rule_3, rule_4 etc.?
# processed_data.append(rule(datum))
我认为 Stack Overflow 上的 this answer 与我正在尝试做的非常接近,但我想向 Python 有经验的人学习如何最好地处理它。我用 'dispatch' 标记了这个 post,我认为这是我想要实现的目标的术语(?)在此先感谢您的帮助和建议!
如评论所述,您非常接近。您需要做的就是在遍历时调用 rule
。
关于处理不同长度的参数,您可以选择在规则中使用 *args
和 **kwargs
。这是一个简单的例子:
def rule1(*args, **kwargs):
# Handling of non-keyword params passed in, if any
if args:
for arg in args:
print(f'{arg} is type {type(arg)}')
# if kwargs is not necessary if you don't intend to handle keyword params
def rule2(*args, **kwargs):
# if args is not necessary if you don't intend to handle non-keyword params
# handling of keyword params passed in, if any
if kwargs:
for k, v in kwargs.items():
print(f'Keyword arg {k} has value {v}')
rule_book = [rule2, rule1]
for rule in rule_book:
# iterate through the rule_book with the same amount of args and kwargs
rule('I am a string', 123, ('This', 'is', 'Tuple'), my_list=[0, 1, 2], my_dict={'A': 0, 'B': 1})
结果:
Keyword arg my_list has value [0, 1, 2]
Keyword arg my_dict has value {'A': 0, 'B': 1}
I am a string is type <class 'str'>
123 is type <class 'int'>
('This', 'is', 'Tuple') is type <class 'tuple'>
关键是要保持规则之间的参数一致,一旦传入所有内容,只需获取相关对象并使用它:
def rule3(*args, **kwargs):
if args:
for arg in args:
if isinstance(arg, tuple):
# if there's a tuple presented, reverse each of the inner items
print([a[::-1] for a in arg])
# ['sihT', 'si', 'elpuT']
根据您构建代码的方式,我相信您应该能够理解并将其应用到您自己的代码中。