hoj*_*oju 17 python arguments list
我有一个函数,其输入参数可以是元素或元素列表.如果这个参数是单个元素,那么我将它放在一个列表中,这样我就可以以一致的方式迭代输入.
目前我有这个:
def my_func(input):
if not isinstance(input, list): input = [input]
for e in input:
...
Run Code Online (Sandbox Code Playgroud)
我正在使用现有的API,因此无法更改输入参数.使用isinstance()感觉hacky,所以有一个正确的方法来做到这一点?
Ale*_*lli 14
通常情况下,字符串(plain和unicode)是你想要作为"单个元素"的唯一迭代 - basestring内置存在特定于让你测试任何一种字符串isinstance,所以对于那个特殊情况它是非常难以理解的;-).
所以我对最常见案例的建议方法是:
if isinstance(input, basestring): input = [input]
else:
try: iter(input)
except TypeError: input = [input]
else: input = list(input)
Run Code Online (Sandbox Code Playgroud)
这是将每个可迭代的EXCEPT字符串直接作为列表处理,将字符串和数字以及其他非迭代作为标量(将其规范化为单项列表)的方法.
我明确地列出了各种迭代的列表,所以你知道你可以进一步执行各种列表技巧 - 排序,迭代不止一次,添加或删除项目以方便迭代等,所有这些都不需要改变ACTUAL输入列表(如果列表确实是;-).如果您只需要一个简单的for循环,那么最后一步是不必要的(如果输入是一个巨大的打开文件,实际上没有用),我建议使用辅助生成器:
def justLoopOn(input):
if isinstance(input, basestring):
yield input
else:
try:
for item in input:
yield item
except TypeError:
yield input
Run Code Online (Sandbox Code Playgroud)
现在,在你需要这种参数规范化的每一个函数中,你只需使用:
for item in justLoopOn(input):
Run Code Online (Sandbox Code Playgroud)
您可以使用辅助规范化功能,即使在另一种情况下(您需要一个真正的列表以用于进一步的恶意目的); 实际上,在这种(更罕见的)情况下,您可以这样做:
thelistforme = list(justLoopOn(input))
Run Code Online (Sandbox Code Playgroud)
所以(不可避免地)有点毛茸茸的归一化逻辑只是在一个地方,就像应该的那样! - )
Pau*_*McG 10
我喜欢Andrei Vajna的建议hasattr(var,'__iter__').请注意一些典型Python类型的结果:
>>> hasattr("abc","__iter__")
False
>>> hasattr((0,),"__iter__")
True
>>> hasattr({},"__iter__")
True
>>> hasattr(set(),"__iter__")
True
Run Code Online (Sandbox Code Playgroud)
这具有将字符串视为不可迭代的附加优点 - 字符串是灰色区域,因为有时您希望将它们视为元素,其他时候将其视为字符序列.
请注意,在Python 3中,str类型确实具有该__iter__属性,但这不起作用:
>>> hasattr("abc", "__iter__")
True
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
21494 次 |
| 最近记录: |