Bla*_*ard 68 python replace nan dataframe pandas
是否有任何方法可以None在Python 中用Pandas 替换值?
您可以使用df.replace('pre', 'post')并可以将值替换为另一个值,但如果您想要替换None值,则无法执行此操作,如果您尝试,则会得到一个奇怪的结果.
所以这是一个例子:
df = DataFrame(['-',3,2,5,1,-5,-1,'-',9])
df.replace('-', 0)
Run Code Online (Sandbox Code Playgroud)
返回成功的结果.
但,
df.replace('-', None)
Run Code Online (Sandbox Code Playgroud)
返回以下结果:
0
0 - // this isn't replaced
1 3
2 2
3 5
4 1
5 -5
6 -1
7 -1 // this is changed to `-1`...
8 9
Run Code Online (Sandbox Code Playgroud)
为什么会返回这么奇怪的结果?
由于我想将这个数据帧倒入MySQL数据库,因此我无法将NaN值放入数据框中的任何元素中,而是想放入None.当然,您可以先更改'-'为NaN然后转换NaN为None,但我想知道为什么数据框以这种可怕的方式运行.
And*_*den 92
实际上在更高版本的pandas中,这会产生一个TypeError:
df.replace('-', None)
TypeError: If "to_replace" and "value" are both None then regex must be a mapping
Run Code Online (Sandbox Code Playgroud)
您可以通过传递列表或字典来完成:
In [11]: df.replace('-', df.replace(['-'], [None]) # or .replace('-', {0: None})
Out[11]:
0
0 None
1 3
2 2
3 5
4 1
5 -5
6 -1
7 None
8 9
Run Code Online (Sandbox Code Playgroud)
但我建议使用NaN而不是None:
In [12]: df.replace('-', np.nan)
Out[12]:
0
0 NaN
1 3
2 2
3 5
4 1
5 -5
6 -1
7 NaN
8 9
Run Code Online (Sandbox Code Playgroud)
小智 14
where可能就是你要找的东西.所以
data=data.where(data=='-', None)
Run Code Online (Sandbox Code Playgroud)
来自熊猫文档:
where[返回]一个与self相同形状的对象,其对应的条目来自self,其中cond为True,否则来自其他).
Mic*_*ner 12
我更喜欢使用该解决方案replace与dict它的简单和优雅的,因为:
df.replace({'-': None})
Run Code Online (Sandbox Code Playgroud)
您还可以拥有更多替代品:
df.replace({'-': None, 'None': None})
Run Code Online (Sandbox Code Playgroud)
即使对于更大的替代品,在我看来,总是显而易见并清楚什么被什么取代 - 这对于长列表来说更难.
cs9*_*s95 10
在继续这篇文章之前,了解NaN 和 None 之间的区别很重要。一种是浮点类型,另一种是对象类型。Pandas 更适合处理标量类型,因为这些类型的许多方法都可以向量化。Pandas 确实尝试一致地处理 None 和 NaN,但 NumPy 不能。
我的建议(和 Andy 的)是坚持使用 NaN。
但是要回答你的问题...
na_values=['-']参数read_csv如果您从 CSV/Excel 加载此数据,我有好消息要告诉您。您可以在数据加载期间在根处取消此设置,而不必在后续步骤中使用代码编写修复程序。
大多数pd.read_*函数(例如read_csv和read_excel)都接受一个na_values属性。
file.csv
A,B
-,1
3,-
2,-
5,3
1,-2
-5,4
-1,-1
-,0
9,0
Run Code Online (Sandbox Code Playgroud)
现在,要将-字符转换为 NaN,请执行以下操作:
import pandas as pd
df = pd.read_csv('file.csv', na_values=['-'])
df
A B
0 NaN 1.0
1 3.0 NaN
2 2.0 NaN
3 5.0 3.0
4 1.0 -2.0
5 -5.0 4.0
6 -1.0 -1.0
7 NaN 0.0
8 9.0 0.0
Run Code Online (Sandbox Code Playgroud)
其他功能/文件格式也类似。
PS:在 v0.24+ 上,即使您的列有 NaN,您也可以保留整数类型(是的,谈论吃蛋糕和吃蛋糕)。您可以指定dtype='Int32'
df = pd.read_csv('file.csv', na_values=['-'], dtype='Int32')
df
A B
0 NaN 1
1 3 NaN
2 2 NaN
3 5 3
4 1 -2
5 -5 4
6 -1 -1
7 NaN 0
8 9 0
df.dtypes
A Int32
B Int32
dtype: object
Run Code Online (Sandbox Code Playgroud)
dtype 不是传统的 int 类型……而是一个Nullable Integer 类型。还有其他选择。
pd.to_numeric与errors='coerce如果你正在处理的数字数据,更快的解决方案是使用pd.to_numeric与errors='coerce'参数,它强制转换无效值(值不能转换为数字)为NaN。
pd.to_numeric(df['A'], errors='coerce')
0 NaN
1 3.0
2 2.0
3 5.0
4 1.0
5 -5.0
6 -1.0
7 NaN
8 9.0
Name: A, dtype: float64
Run Code Online (Sandbox Code Playgroud)
要保留(可为空)整数 dtype,请使用
pd.to_numeric(df['A'], errors='coerce').astype('Int32')
0 NaN
1 3
2 2
3 5
4 1
5 -5
6 -1
7 NaN
8 9
Name: A, dtype: Int32
Run Code Online (Sandbox Code Playgroud)
要强制多列,请使用apply:
df[['A', 'B']].apply(pd.to_numeric, errors='coerce').astype('Int32')
A B
0 NaN 1
1 3 NaN
2 2 NaN
3 5 3
4 1 -2
5 -5 4
6 -1 -1
7 NaN 0
8 9 0
Run Code Online (Sandbox Code Playgroud)
...并在之后分配结果。
更多信息可以在这个答案中找到。
对于 Pandas 版本 \xe2\x89\xa51.0.0,我将使用DataFrame.replaceor Series.replace:
df.replace(old_val, pd.NA, inplace=True)\nRun Code Online (Sandbox Code Playgroud)\n这样做更好有两个原因:
\npd.NA代替None或np.nan。