如何在Python中将字符串转换为布尔值?这个尝试返回True:
>>> bool("False")
True
如何在Python中将字符串转换为布尔值?这个尝试返回True:
>>> bool("False")
True
当前回答
在有限的情况或情况下,您可以对正在处理的数据做出强有力的假设。然而,由于自定义对象可以覆盖Python中的__eq__相等性检查,因此存在一个重要的陷阱。看看下面这个刻意简化的玩具例子:
In [1]: class MyString:
...: def __init__(self, value):
...: self.value = value
...: def __eq__ (self, obj):
...: if hasattr(obj, 'value'):
...: return obj.value == self.value
...: return False
...:
In [2]: v = MyString("True")
In [3]: v == "True"
Out[3]: False
如果你想象有人继承了MyString的字符串类型,或者实现了各种原生字符串方法,repr等,这样MyString实例的行为就和字符串完全一样,但是在相等性检查中有特殊的额外值步骤,那么简单地使用== 'True'将会失败,而且从用户的角度来看,这很可能是一个无声的失败。
这就是为什么将type强制转换为您想要执行的相等性检查的确切性质,将其封装到一个helper函数中,并对依赖这种“已注册”的方式进行验证是一种很好的实践。例如,在MyString中,你可以这样写,
def validate(s):
if isinstance(s, str):
return s == 'True'
elif isinstance(s, MyString):
return s.value == 'True' # <-- business logic
...
raise ValueError(f"Type {type(s)} not supported for validation.")
或者另一种常用的模式是反向透视图,其中您只为验证定义了一种行为,但是您有一个helper函数,它将强制转换为适合于该单一验证行为的类型,例如
def to_str(s):
if isinstance(s, str):
return s
elif isinstance(s, MyString):
return s.value
...
raise ValueError(f"Unsupported type {type(s)}")
def validate(s):
return to_str(s) == 'True'
It might look like we're adding a lot of boilerplate and verbosity. We could glibly express critique by saying, "why write all that if you can just write s == 'True'?" - But it misses the point that when you are validating something, you need to make sure all of your preconditions hold for the validation logic to be applied. If you can assume some data is a plain str type and you don't need to do any of that precondition (such as type) checking, great - but that's a very rare situation and it can be misleading to characterize the general situation for this question as being amenable to one super short and concise equality check.
其他回答
这是我写的版本。将其他几个解决方案合并为一个。
def to_bool(value):
"""
Converts 'something' to boolean. Raises exception if it gets a string it doesn't handle.
Case is ignored for strings. These string values are handled:
True: 'True', "1", "TRue", "yes", "y", "t"
False: "", "0", "faLse", "no", "n", "f"
Non-string values are passed to bool.
"""
if type(value) == type(''):
if value.lower() in ("yes", "y", "true", "t", "1"):
return True
if value.lower() in ("no", "n", "false", "f", "0", ""):
return False
raise Exception('Invalid value for boolean conversion: ' + value)
return bool(value)
如果它得到一个字符串,它期望特定的值,否则引发异常。如果它没有得到一个字符串,就让bool构造函数来计算它。测试这些案例:
test_cases = [
('true', True),
('t', True),
('yes', True),
('y', True),
('1', True),
('false', False),
('f', False),
('no', False),
('n', False),
('0', False),
('', False),
(1, True),
(0, False),
(1.0, True),
(0.0, False),
([], False),
({}, False),
((), False),
([1], True),
({1:2}, True),
((1,), True),
(None, False),
(object(), True),
]
这是我的版本。它同时检查正值和负值列表,对于未知值引发异常。它不接收字符串,但任何类型都可以。
def to_bool(value):
"""
Converts 'something' to boolean. Raises exception for invalid formats
Possible True values: 1, True, "1", "TRue", "yes", "y", "t"
Possible False values: 0, False, None, [], {}, "", "0", "faLse", "no", "n", "f", 0.0, ...
"""
if str(value).lower() in ("yes", "y", "true", "t", "1"): return True
if str(value).lower() in ("no", "n", "false", "f", "0", "0.0", "", "none", "[]", "{}"): return False
raise Exception('Invalid value for boolean conversion: ' + str(value))
示例:
>>> to_bool(True)
True
>>> to_bool("tRUe")
True
>>> to_bool("1")
True
>>> to_bool(1)
True
>>> to_bool(2)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 9, in to_bool
Exception: Invalid value for boolean conversion: 2
>>> to_bool([])
False
>>> to_bool({})
False
>>> to_bool(None)
False
>>> to_bool("Wasssaaaaa")
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 9, in to_bool
Exception: Invalid value for boolean conversion: Wasssaaaaa
>>>
该版本保留了int(value)等构造函数的语义,并提供了一种简单的方法来定义可接受的字符串值。
def to_bool(value):
valid = {'true': True, 't': True, '1': True,
'false': False, 'f': False, '0': False,
}
if isinstance(value, bool):
return value
if not isinstance(value, basestring):
raise ValueError('invalid literal for boolean. Not a string.')
lower_value = value.lower()
if lower_value in valid:
return valid[lower_value]
else:
raise ValueError('invalid literal for boolean: "%s"' % value)
# Test cases
assert to_bool('true'), '"true" is True'
assert to_bool('True'), '"True" is True'
assert to_bool('TRue'), '"TRue" is True'
assert to_bool('TRUE'), '"TRUE" is True'
assert to_bool('T'), '"T" is True'
assert to_bool('t'), '"t" is True'
assert to_bool('1'), '"1" is True'
assert to_bool(True), 'True is True'
assert to_bool(u'true'), 'unicode "true" is True'
assert to_bool('false') is False, '"false" is False'
assert to_bool('False') is False, '"False" is False'
assert to_bool('FAlse') is False, '"FAlse" is False'
assert to_bool('FALSE') is False, '"FALSE" is False'
assert to_bool('F') is False, '"F" is False'
assert to_bool('f') is False, '"f" is False'
assert to_bool('0') is False, '"0" is False'
assert to_bool(False) is False, 'False is False'
assert to_bool(u'false') is False, 'unicode "false" is False'
# Expect ValueError to be raised for invalid parameter...
try:
to_bool('')
to_bool(12)
to_bool([])
to_bool('yes')
to_bool('FOObar')
except ValueError, e:
pass
您可能已经有了一个解决方案,但对于其他人来说,他们正在寻找一种方法,将值转换为布尔值,使用“标准”假值,包括None,[],{}和“”,除了false, no和0。
def toBoolean( val ):
"""
Get the boolean value of the provided input.
If the value is a boolean return the value.
Otherwise check to see if the value is in
["false", "f", "no", "n", "none", "0", "[]", "{}", "" ]
and returns True if value is not in the list
"""
if val is True or val is False:
return val
falseItems = ["false", "f", "no", "n", "none", "0", "[]", "{}", "" ]
return not str( val ).strip().lower() in falseItems
下面是我用来评估字符串真实性的东西:
def as_bool(val):
if val:
try:
if not int(val): val=False
except: pass
try:
if val.lower()=="false": val=False
except: pass
return bool(val)
与使用eval的结果大致相同,但更安全。