2

我想迭代一个可以是列表或字符串的变量。问题是,我不想将字符串视为字符列表:

[1, 2, 3] => [1, 2, 3]
["1", "2"] => ["1", "2"]
"123" => ["123"] # instead of ["1", "2", "3"]

for x in foo适用于列表,但假设 foo 是一个字符串,则迭代字符。

我知道这可以通过检查类型(例如for x in (foo if type(foo) is list else [foo]))来完成,但我觉得必须有更好的方法......

4

2 回答 2

6

直接的方法确实是

for x in ([foo] if isinstance(foo, basestring) else foo)

为什么我说isinstance(foo, basestring)而不是说type(foo) is list

  • 您的代码更有可能包含一些非列表序列对象,而非字符串类字符串对象非常罕见。

  • 正如Alex Martelli 解释的那样,使用它isinstance比检查确切的类型相等性更好,这样您还可以包含子类。

  • 具体来说,您可能希望以相同的方式处理字节和 Unicode 字符串。

Alex 说测试类型很丑陋,总的来说我同意,但是如果您需要以一种方式写出字符串并列出另一种方式,那么这是正确的方法。

于 2013-05-30T07:16:59.417 回答
2

在不知道你究竟为什么这样做的情况下 - 我相信你有充分的理由,我想指出,这可能是一种代码味道......

最有可能的是,您在调用函数之前就知道您有一个列表还是一个字符串。调用函数时编写两个函数或将字符串装箱。瞧。无需检查类型。

如果你不知道你有什么样的结果,但应该(因为你想根据类型不同地对待它)那也是一种代码异味——在你的代码中的某个地方,你不太清楚正在发生什么或者某些子系统的接口太模糊。

所以。要么解决根本原因。或检查函数内的类型。

于 2013-05-30T07:23:59.667 回答