Python: most idiomatic way to convert None to empty string?
做以下事情的最惯用方法是什么?
1 2 3 4 5 6 7
| def xstr(s):
if s is None:
return ''
else:
return s
s = xstr(a) + xstr(b) |
更新:我正在使用Tryptich的建议来使用str(s),这使得这个例程适用于除字符串之外的其他类型。 Vinay Sajip的lambda建议给我留下了深刻的印象,但我希望保持我的代码相对简单。
1 2 3 4 5
| def xstr(s):
if s is None:
return ''
else:
return str(s) |
-
我喜欢你的原始语法。 我认为它已经非常清晰易读。
-
@GuiSim:我可能有偏见,但我的回答几乎就像一个普通的英语句子......
-
"如果s为None,则返回一个空字符串;否则,返回[string of] s。" 问题的代码也像普通的英语句子一样。
-
a)如果字符串s来自未找到密钥的字典查找,则使用dict.get(key, '')
-
b)如果你只想将这个字符串转换用于输出格式化(例如打印),那么你可以直接做'... {}'。format(dict.get(1))`
1 2
| def xstr(s):
return '' if s is None else str(s) |
-
我认为这需要Python 2.6或更高版本。 (但是,对于第一个近似,理智也是如此。)
-
对我来说2.5的工作就好了。
-
这个语法是在2.5中引入的;对于早期版本的Python,您可以使用return s is not None and s or ''。
-
是否有未来声明在2.4中启用它?
-
我转过身来强调更多的commen案例:如果s不是,则返回s别"
-
@Ber:我会保持原样,避免双重否定。
-
这是.. and .. or ..失败的一个很好的例子,为什么if-else是首选。 s is not None and s or ''中有两个微妙的错误。
-
return '' if not s else str(s)
-
@Iqbal如果您要与None进行比较,请始终使用is或is not。更多信息
如果您知道该值将始终为字符串或None:
1 2 3 4 5 6
| xstr = lambda s: s or""
print xstr("a") + xstr("b") # -> 'ab'
print xstr("a") + xstr(None) # -> 'a'
print xstr(None) + xstr("b") # -> 'b'
print xstr(None) + xstr(None) # -> '' |
-
到目前为止最pythonic。使用python将None,空列表,空字符串,0等视为false的事实。还使用or语句返回第一个元素为true或最后一个元素给or或(或ors组)的事实。这也使用lambda函数。我会给你+10,但很明显它不会让我。
-
这将转换为0和False(以及传递给bool()时评估为False的任何其他内容)
-
我不认为它是"迄今为止最为pythonic"。这是其他语言中常见的习惯用语,我不认为在Python中使用它是错误的,但是为了避免这样的技巧而精确引入的条件表达式。
-
我不认为这是条件表达式背后的原因。它也不是特别棘手 - 除了它干净整洁外,没有什么特别之处。我建议只使用它,如果你知道s总是一个字符串或无 - 正如我在介绍中所说的那样。如果是这种情况,这似乎是最紧凑的方式。
-
这使得[],{}等给出与None相同的结果,这是不希望的。特别地,xstr(False)应该是"False"而不是""。滥用lambdas是一个糟糕的例子,使用def xstr(s): return s or""你想要将它全部放在一行上。
-
请注意,我在一开始就用"如果您知道值将始终为字符串或无"来限定我的答案。
-
当我们知道s总是字符串或None时,我发现这非常有用。处理re.match(pattern,string).groups()的结果时会发生这种情况。
如果您确实希望函数的行为类似于str()内置函数,但在参数为None时返回空字符串,请执行以下操作:
1 2 3 4
| def xstr(s):
if s is None:
return ''
return str(s) |
-
我保留了其他,但感谢str(s)提示,因此可以处理多种类型。太好了!
-
或者只是xstr = lambda s: '' if s is None else str(s)
-
我喜欢输入if not s:而不是if s is None
-
@guneysus他们不一样:not False == True但是False is None == False。
-
谢谢@Lynn你是对的。我意识到自己的错。但我知道(或假设)s始终是str / unicode类型或None。是的,False是一个值,但我更喜欢这种方式来节省我的键盘和眼睛;)
-
@guneysus还在。如果你想字符串化False,你可以做str(False),但你的xtr(False)将返回''。取决于你想拥有的行为,而不是你喜欢或不喜欢打字not s
可能是最短的
str(s or '')
因为None是False,如果x是false,"x或y"返回y。有关详细说明,请参阅布尔运算符。这很简短,但不是很明确。
-
这太好了,谢谢!从来没有想过用这种方式使用or
-
如果s为0,False或任何虚假值,则此操作无效
-
好吧,在操作要求中没有提到,所以我在这里看不到你的观点。
-
@dorvak OP非常清楚输出应该是'' iff s is None的要求。所有其他输入应返回s(或修订后的请求中的str(s))。
-
str(...)只围绕s,将空字符串转换为字符串是一个废话......也是修改后的请求:def xstr(s): return str(s) or""
-
@fortea:那不行。如果s是None,则xstr()的结果应为空字符串,但str(None)给出字符串"None",这是返回的内容(因为字符串"None"不是虚假值。
return s or ''可以很好地解决您所说的问题!
-
值得注意的是,当s为False或0时(这不是原始字符串问题,而是更新的字符串问题),这将给出不同的结果。)
-
@Oddthinking s = False或s = 0很可能是它使用中的边缘情况,可以通过将其写为return str(s or '')来轻松减轻
-
@WillemvanKetwich:这有完全相同的问题:s(False)应该返回'False',而不是''。 s(0)应该返回'0',而不是''。同样,对于定义__bool__或__nonzero__的对象。
-
@Oddthinking我明白你的观点。在任何情况下,如果它专门用于字符串对象,例如OP的问题,它应该不是问题。
-
@WillemvanKetwich:在我的评论中查看更新的问题和警告 - 这已被涵盖,
-
就像对@ Krystian-Cybulski的aswer的评论一样:把str(...)放在s:def xstr(s): return str(s) or""
1 2
| def xstr(s):
return s or"" |
-
这将为0,[],{},False和类似虚假的值返回'',这不是海报要求的。
-
把str([...])放在s:def xstr(s): return str(s) or"" 周围
功能方式(单线)
1
| xstr = lambda s: '' if s is None else s |
-
"def xstr(s):return''如果s是None,则s"也是一个on-liner,python对于空格不是那么严格
-
它不是真正的单行,它只是写在一行g
-
在什么意义上它不是一个真正的在线人?检查你的口译员 - 这不是语法错误。对于所有意图和目的,它比lambda ^ _ ^更真实
-
你应该使用def而不是将lambda赋值给变量的PEP 8种。 lambda唯一真正的优点是你可以写作表达式的一部分(例如传递给另一个函数),并且这样的代码会丢失这种优势。我曾经这样做,直到我注意到def可以写成一行,然后PEP 8告诉我要走的路。总是跟着Python神。
1 2
| def xstr(s):
return {None:''}.get(s, s) |
-
我认为,这是相当pythonic的 - 这个怎么样:"xstr = lambda s:{None:''}。get(s,s)" - 将整个事物简化为单行。
-
不必要的慢(额外的字典构造和查找),并且更难阅读。非常unpythonic。
-
你是对的。它相当perlish但它避免了python字节码中的条件跳转。
-
get()函数调用意味着至少有一个额外的条件跳转。
-
在不知道问题或查找get的情况下,我无法说出这应该做什么。
-
达里奥:有多少语言功能(用任何语言)你能说出他们做什么而不知道他们并且没有查找它们?
在一些其他答案的基础上做一个整洁的单行:
1
| s = (lambda v: v or '')(a) + (lambda v: v or '')(b) |
甚至只是:
1
| s = (a or '') + (b or '') |
-
为什么甚至提到(lambda v: v or '')?
-
为什么不? 价格为1的2个提示!??
我使用max函数:
1 2
| max(None, '') #Returns blank
max("Hello",'') #Returns Hello |
像魅力一样工作;)只需将您的字符串放在函数的第一个参数中。
-
这是因为'str'>'NoneType',并且是特定于CPython的。 从手册:"除了数字之外的不同类型的对象按其类型名称排序"。 此外,这在Python 3000中不起作用,因为不再允许类型间比较(TypeError:unorderable types:str()> NoneType())。 请参阅Python如何比较字符串和int?
-
很高兴知道谢谢,所以不是一个好主意继续使用python 3.x兼容代码。
如果您需要与Python 2.4兼容,请修改上述内容
1
| xstr = lambda s: s is not None and s or '' |
如果只是格式化字符串,您可以执行以下操作:
1 2 3 4 5 6 7 8 9
| from string import Formatter
class NoneAsEmptyFormatter(Formatter):
def get_value(self, key, args, kwargs):
v = super().get_value(key, args, kwargs)
return '' if v is None else v
fmt = NoneAsEmptyFormatter()
s = fmt.format('{}{}', a, b) |
在下面解释的场景中,我们总是可以避免类型转换
1 2 3 4 5 6
| customer ="John"
name = str(customer)
if name is None
print"Name is blank"
else:
print"Customer name :" + name |
在上面的示例中,如果变量customer的值为None,则在分配给'name'时它会进一步转换。 'if'子句中的比较总是会失败。
1 2 3 4 5 6
| customer ="John" # even though its None still it will work properly.
name = customer
if name is None
print"Name is blank"
else:
print"Customer name :" + str(name) |
以上示例将正常工作。当从URL,JSON或XML获取值时,这种情况非常常见,甚至值也需要进行任何操作的进一步类型转换。
1 2 3 4
| def xstr(s):
return s if s else ''
s ="%s%s" % (xstr(a), xstr(b)) |
-
这将为所有类似虚假的值返回一个空字符串,这不是海报要求的。
使用短路评估:
由于+对字符串不是很好的操作,因此最好使用格式字符串:
1
| s ="%s%s" % (a or '', b or '') |
-
有没有听说过DRY?
-
对于所有类似虚假的值,这也会将'a'转换为空字符串,而不仅仅是None。例如,空元组,列表和dicts将转换为空字符串,这不是OP指定的。
-
+是两个字符串的完美操作符。当你试图用它来加入几十个你遇到麻烦的时候。对于两个,它可能比其他选项更快;无论哪种方式,它都在噪音中。
-
对我而言+1是因为这正是我在我的情况下所需要的:lambda或函数来替换单个运算符(or)对我来说似乎有点矫枉过正...我没有其他错误值的情况 - 要么str或者没有。除了+运算符的注释,这可能取决于具体的情况,可能需要基准测试,这个答案不值得-1