使用 str.contains 忽略 NaN
Posted
技术标签:
【中文标题】使用 str.contains 忽略 NaN【英文标题】:Ignoring NaNs with str.contains 【发布时间】:2015-04-03 09:37:28 【问题描述】:我想查找包含字符串的行,如下所示:
DF[DF.col.str.contains("foo")]
但是,这会失败,因为某些元素是 NaN:
ValueError: 无法使用包含 NA / NaN 值的向量进行索引
所以我求助于混淆
DF[DF.col.notnull()][DF.col.dropna().str.contains("foo")]
有没有更好的办法?
【问题讨论】:
【参考方案1】:有一个标志:
In [11]: df = pd.DataFrame([["foo1"], ["foo2"], ["bar"], [np.nan]], columns=['a'])
In [12]: df.a.str.contains("foo")
Out[12]:
0 True
1 True
2 False
3 NaN
Name: a, dtype: object
In [13]: df.a.str.contains("foo", na=False)
Out[13]:
0 True
1 True
2 False
3 False
Name: a, dtype: bool
请参阅str.replace
文档:
na : 默认 NaN,缺失值的填充值。
因此您可以执行以下操作:
In [21]: df.loc[df.a.str.contains("foo", na=False)]
Out[21]:
a
0 foo1
1 foo2
【讨论】:
在这里,我遇到了一种情况,a
是从 CSV 填充的,a
列包含字符串“nan”。 pandas
“智能”将其转换为NaN
,并在我尝试执行df.a.str.contains()
时开始抱怨。所以是的protip:确保在read_csv()
中设置列类型,或者之后执行df = df.where(pandas.notnull(df), "nan")
之类的操作 LOL
你救了我...如果这不在这里,我想我会经历两周的噩梦,把我的头撞到墙上:-) 绝对值得+1,哈哈
大声笑为什么不是这个默认值?
宾果游戏。这应该是默认标志!
希望 na
提供其他 str 函数,例如 str.extract()。【参考方案2】:
import folium
import pandas
data= pandas.read_csv("maps.txt")
lat = list(data["latitude"])
lon = list(data["longitude"])
map= folium.Map(location=[31.5204, 74.3587], zoom_start=6, tiles="Mapbox Bright")
fg = folium.FeatureGroup(name="My Map")
for lt, ln in zip(lat, lon):
c1 = fg.add_child(folium.Marker(location=[lt, ln], popup="Hi i am a Country",icon=folium.Icon(color='green')))
child = fg.add_child(folium.Marker(location=[31.5204, 74.5387], popup="Welcome to Lahore", icon= folium.Icon(color='green')))
map.add_child(fg)
map.save("Lahore.html")
Traceback (most recent call last):
File "C:\Users\Ryan\AppData\Local\Programs\Python\Python36-32\check2.py", line 14, in <module>
c1 = fg.add_child(folium.Marker(location=[lt, ln], popup="Hi i am a Country",icon=folium.Icon(color='green')))
File "C:\Users\Ryan\AppData\Local\Programs\Python\Python36-32\lib\site-packages\folium\map.py", line 647, in __init__
self.location = _validate_coordinates(location)
File "C:\Users\Ryan\AppData\Local\Programs\Python\Python36-32\lib\site-packages\folium\utilities.py", line 48, in _validate_coordinates
'got:\n!r'.format(coordinates))
ValueError: Location values cannot contain NaNs, got:
[nan, nan]
【讨论】:
这不是答案。【参考方案3】:除了以上答案,我想说对于没有单个单词名称的列,您可以使用:-
df[df['Product ID'].str.contains("foo") == True]
希望这会有所帮助。
【讨论】:
【参考方案4】:我不是 100% 知道为什么(实际上是来这里寻找答案),但这也有效,并且不需要替换所有 nan 值。
import pandas as pd
import numpy as np
df = pd.DataFrame([["foo1"], ["foo2"], ["bar"], [np.nan]], columns=['a'])
newdf = df.loc[df['a'].str.contains('foo') == True]
使用或不使用.loc
。
我不知道为什么会这样,因为我理解当您使用括号进行索引时,pandas 会将括号内的任何内容评估为True
或False
。我不知道为什么让括号内的短语“extra boolean”有任何效果。
【讨论】:
【参考方案5】:你也可以模仿:
DF[DF.col.str.contains(pat = '(foo)', regex = True) ]
【讨论】:
【参考方案6】:df[df.col.str.contains("foo").fillna(False)]
【讨论】:
【参考方案7】:您也可以使用query
方法通过布尔表达式查询DataFrame的列,如下所示:
df.query('a.str.contains("foo", na=False)')
请注意,您可能不会获得性能改进,但它更具可读性(可以说)。
【讨论】:
以上是关于使用 str.contains 忽略 NaN的主要内容,如果未能解决你的问题,请参考以下文章
如何在 pandas str.contains 中使用 \b 单词边界?
使用str.contains()在加号(+)之后找不到字符串
识别包含单词的句子,并使用 str.contains 在列中显示该单词