如何在熊猫数据框架的一列中用零替换NaN值?

我有一个熊猫数据框架如下:

      itm Date                  Amount
67    420 2012-09-30 00:00:00   65211
68    421 2012-09-09 00:00:00   29424
69    421 2012-09-16 00:00:00   29877
70    421 2012-09-23 00:00:00   30990
71    421 2012-09-30 00:00:00   61303
72    485 2012-09-09 00:00:00   71781
73    485 2012-09-16 00:00:00     NaN
74    485 2012-09-23 00:00:00   11072
75    485 2012-09-30 00:00:00  113702
76    489 2012-09-09 00:00:00   64731
77    489 2012-09-16 00:00:00     NaN

当我尝试应用一个函数到金额列,我得到以下错误:

ValueError: cannot convert float NaN to integer
我已经尝试使用数学模块中的.isnan应用一个函数 我已经尝试了pandas .replace属性 我尝试了pandas 0.9中的.sparse data属性 我还尝试了在函数中if NaN == NaN语句。 我还看了我如何替换NA值与零在一个R数据框架?这篇文章,同时也看了其他一些文章。 我尝试过的所有方法都不起作用或不能识别NaN。 任何提示或解决方案将不胜感激
1135932 次浏览

我相信DataFrame.fillna()会为你做到这一点。

链接到一个dataframe一个系列的文档。

例子:

In [7]: df
Out[7]:
0         1
0       NaN       NaN
1 -0.494375  0.570994
2       NaN       NaN
3  1.876360 -0.229738
4       NaN       NaN


In [8]: df.fillna(0)
Out[8]:
0         1
0  0.000000  0.000000
1 -0.494375  0.570994
2  0.000000  0.000000
3  1.876360 -0.229738
4  0.000000  0.000000

若要仅在一列中填充nan,请仅选择该列。在这种情况下,我使用inplace=True来实际改变df的内容。

In [12]: df[1].fillna(0, inplace=True)
Out[12]:
0    0.000000
1    0.570994
2    0.000000
3   -0.229738
4    0.000000
Name: 1


In [13]: df
Out[13]:
0         1
0       NaN  0.000000
1 -0.494375  0.570994
2       NaN  0.000000
3  1.876360 -0.229738
4       NaN  0.000000

编辑:

为了避免SettingWithCopyWarning,使用内置的列特定功能:

df.fillna({1:0}, inplace=True)

我只是想提供一点更新/特殊情况,因为看起来人们仍然来这里。如果您正在使用多索引或其他索引切片器,inplace=True选项可能不足以更新您所选择的切片。例如,在2x2级别的多索引中,这不会改变任何值(例如pandas 0.15):

idx = pd.IndexSlice
df.loc[idx[:,mask_1],idx[mask_2,:]].fillna(value=0,inplace=True)

“问题”是链接破坏了fillna更新原始数据框架的能力。我把“问题”加上引号,是因为在某些情况下,设计决策导致不通过这些链进行解释是有充分理由的。此外,这是一个复杂的示例(尽管我真的遇到了它),但同样的情况可能适用于更少的索引级别,这取决于您如何进行切片。

解决方案是DataFrame.update:

df.update(df.loc[idx[:,mask_1],idx[[mask_2],:]].fillna(value=0))

它是一行,读起来相当好(某种程度上),并消除了任何不必要的中间变量或循环混乱,同时允许您将fillna应用到您喜欢的任何多级切片!

如果有人能找到这个不工作的地方,请在评论中发帖,我一直在搞砸它,看看源代码,它似乎至少解决了我的多索引切片问题。

下面的代码适合我。

import pandas


df = pandas.read_csv('somefile.txt')


df = df.fillna(0)

并不保证切片返回一个视图或副本。你可以这样做

df['column'] = df['column'].fillna(value)

你可以使用replaceNaN改为0:

import pandas as pd
import numpy as np


# for column
df['column'] = df['column'].replace(np.nan, 0)


# for whole dataframe
df = df.replace(np.nan, 0)


# inplace
df.replace(np.nan, 0, inplace=True)

填补缺失值的简单方法:-

填充 字符串列:当字符串列有缺失值和NaN值时。

df['string column name'].fillna(df['string column name'].mode().values[0], inplace = True)

当数值列有缺失值和NaN值时,填充 数字列:

df['numeric column name'].fillna(df['numeric column name'].mean(), inplace = True)

用零填充NaN:

df['column name'].fillna(0, inplace = True)

enter image description here

考虑到上表中的特定列Amount是整数类型。以下是一个解决方案:

df['Amount'] = df.Amount.fillna(0).astype(int)

类似地,您可以用各种数据类型填充它,如floatstr等。

特别地,我会考虑datatype来比较同一列的不同值。

替换熊猫中的na值

df['column_name'].fillna(value_to_be_replaced,inplace=True)

如果inplace = False,而不是更新df (dataframe),它将返回修改后的值。

如果要将其转换为熊猫数据框架,也可以使用fillna来完成。

import numpy as np
df=np.array([[1,2,3, np.nan]])


import pandas as pd
df=pd.DataFrame(df)
df.fillna(0)

这将返回以下内容:

     0    1    2   3
0  1.0  2.0  3.0 NaN
>>> df.fillna(0)
0    1    2    3
0  1.0  2.0  3.0  0.0

您还可以使用字典来填充DataFrame中特定列的NaN值,而不是用一些oneValue填充所有DF。

import pandas as pd


df = pd.read_excel('example.xlsx')
df.fillna( {
'column1': 'Write your values here',
'column2': 'Write your values here',
'column3': 'Write your values here',
'column4': 'Write your values here',
.
.
.
'column-n': 'Write your values here'} , inplace=True)

主要有两种选择;如果只使用数值替换来填充缺失值NaN / np.nan(跨列):

df['Amount'].fillna(value=None, method= ,axis=1,)是足够的:

来自文档:

值:标量,字典,系列或数据帧 值用于填充孔(例如0),交替使用a dict/Series/DataFrame的值,指定用于哪个值 每个索引(对于Series)或列(对于DataFrame)。(值不 在dict/Series/DataFrame中将不会被填充)。此值不能

这意味着'字符串'或'常量'不再允许被赋值。

对于更专业的impueration,使用SimpleImputer ():

from sklearn.impute import SimpleImputer
si = SimpleImputer(strategy='constant', missing_values=np.nan, fill_value='Replacement_Value')
df[['Col-1', 'Col-2']] = si.fit_transform(X=df[['C-1', 'C-2']])


用不同的方法替换不同列中的nan:

   replacement= {'column_A': 0, 'column_B': -999, 'column_C': -99999}
df.fillna(value=replacement)

如果你想为一个特定的列填充NaN,你可以使用loc:

d1 = {"Col1" : ['A', 'B', 'C'],
"fruits": ['Avocado', 'Banana', 'NaN']}
d1= pd.DataFrame(d1)


output:


Col1    fruits
0   A   Avocado
1   B   Banana
2   C   NaN




d1.loc[ d1.Col1=='C', 'fruits' ] =  'Carrot'




output:


Col1    fruits
0   A   Avocado
1   B   Banana
2   C   Carrot

将所有nan替换为0

df = df.fillna(0)

这对我有用,但没人提过。会有什么问题吗?

df.loc[df['column_name'].isnull(), 'column_name'] = 0

已经有很多贡献了,但因为我是新来的,我仍然会提供意见。

在Pandas DataFrame中,有两种方法将NaN值替换为0:

  1. fillna():函数使用指定的方法填充NA/NaN值。
  2. Replace (): df.replace()一个简单的方法,用于替换字符串,正则表达式,列表,字典

例子:

#NaN with zero on all columns
df2 = df.fillna(0)




#Using the inplace=True keyword in a pandas method changes the default behaviour.
df.fillna(0, inplace = True)


# multiple columns appraoch
df[["Student", "ID"]] = df[["Student", "ID"]].fillna(0)

最后是replace()方法:

df["Student"] = df["Student"].replace(np.nan, 0)
我认为这也是值得提及和解释的 fillna()的参数配置 如方法,轴,限制等

从我们的文档来看:

Series.fillna(value=None, method=None, axis=None,
inplace=False, limit=None, downcast=None)
Fill NA/NaN values using the specified method.

参数

value [scalar, dict, Series, or DataFrame] Value to use to
fill holes (e.g. 0), alternately a dict/Series/DataFrame
of values specifying which value to use for each index
(for a Series) or column (for a DataFrame). Values not in
the dict/Series/DataFrame will not be filled. This
value cannot be a list.


method [{‘backfill’, ‘bfill’, ‘pad’, ‘ffill’, None},
default None] Method to use for filling holes in
reindexed Series pad / ffill: propagate last valid
observation forward to next valid backfill / bfill:
use next valid observation to fill gap axis
[{0 or ‘index’}] Axis along which to fill missing values.


inplace [bool, default False] If True, fill
in-place. Note: this will modify any other views
on this object (e.g., a no-copy slice for a
column in a DataFrame).


limit [int,defaultNone] If method is specified,
this is the maximum number of consecutive NaN
values to forward/backward fill. In other words,
if there is a gap with more than this number of
consecutive NaNs, it will only be partially filled.
If method is not specified, this is the maximum
number of entries along the entire axis where NaNs
will be filled. Must be greater than 0 if not None.


downcast [dict, default is None] A dict of item->dtype
of what to downcast if possible, or the string ‘infer’
which will try to downcast to an appropriate equal
type (e.g. float64 to int64 if possible).
< p > Ok。让我们从method=参数this开始 有正向填充(ffill)和反向填充(bfill) Ffill正在复制前面的内容

例如:

import pandas as pd
import numpy as np
inp = [{'c1':10, 'c2':np.nan, 'c3':200}, {'c1':np.nan,'c2':110, 'c3':210}, {'c1':12,'c2':np.nan, 'c3':220},{'c1':12,'c2':130, 'c3':np.nan},{'c1':12,'c2':np.nan, 'c3':240}]
df = pd.DataFrame(inp)


c1       c2      c3
0   10.0     NaN      200.0
1   NaN   110.0 210.0
2   12.0     NaN      220.0
3   12.0     130.0 NaN
4   12.0     NaN      240.0

填充:

df.fillna(method="ffill")


c1     c2      c3
0   10.0      NaN 200.0
1   10.0    110.0   210.0
2   12.0    110.0   220.0
3   12.0    130.0   220.0
4   12.0    130.0   240.0

向后填:

df.fillna(method="bfill")


c1      c2     c3
0   10.0    110.0   200.0
1   12.0    110.0   210.0
2   12.0    130.0   220.0
3   12.0    130.0   240.0
4   12.0      NaN   240.0

Axis参数帮助我们选择填充的方向:

填补方向:

ffill:

Axis = 1
Method = 'ffill'
----------->
direction


df.fillna(method="ffill", axis=1)


c1   c2      c3
0   10.0     10.0   200.0
1    NaN    110.0   210.0
2   12.0     12.0   220.0
3   12.0    130.0   130.0
4   12.0    12.0    240.0


Axis = 0 # by default
Method = 'ffill'
|
|       # direction
|
V
e.g: # This is the ffill default
df.fillna(method="ffill", axis=0)


c1     c2      c3
0   10.0      NaN   200.0
1   10.0    110.0   210.0
2   12.0    110.0   220.0
3   12.0    130.0   220.0
4   12.0    130.0   240.0

bfill:

axis= 0
method = 'bfill'
^
|
|
|
df.fillna(method="bfill", axis=0)


c1     c2      c3
0   10.0    110.0   200.0
1   12.0    110.0   210.0
2   12.0    130.0   220.0
3   12.0    130.0   240.0
4   12.0      NaN   240.0


axis = 1
method = 'bfill'
<-----------
df.fillna(method="bfill", axis=1)
c1     c2       c3
0    10.0   200.0   200.0
1   110.0   110.0   210.0
2    12.0   220.0   220.0
3    12.0   130.0     NaN
4    12.0   240.0   240.0


# alias:
#  'fill' == 'pad'
#   bfill == backfill

极限参数:

df
c1     c2      c3
0   10.0      NaN   200.0
1    NaN    110.0   210.0
2   12.0      NaN   220.0
3   12.0    130.0     NaN
4   12.0      NaN   240.0

只替换跨列的第一个NaN元素:

df.fillna(value = 'Unavailable', limit=1)
c1           c2          c3
0          10.0 Unavailable       200.0
1   Unavailable       110.0       210.0
2          12.0         NaN       220.0
3          12.0       130.0 Unavailable
4          12.0         NaN       240.0


df.fillna(value = 'Unavailable', limit=2)


c1            c2          c3
0          10.0 Unavailable       200.0
1   Unavailable       110.0       210.0
2          12.0 Unavailable       220.0
3          12.0       130.0 Unavailable
4          12.0         NaN       240.0

低垂的参数:

df.info()
<class 'pandas.core.frame.DataFrame'>
RangeIndex: 5 entries, 0 to 4
Data columns (total 3 columns):
#   Column  Non-Null Count  Dtype
---  ------  --------------  -----
0   c1      4 non-null      float64
1   c2      2 non-null      float64
2   c3      4 non-null      float64
dtypes: float64(3)
memory usage: 248.0 bytes


df.fillna(method="ffill",downcast='infer').info()
<class 'pandas.core.frame.DataFrame'>
RangeIndex: 5 entries, 0 to 4
Data columns (total 3 columns):
#   Column  Non-Null Count  Dtype
---  ------  --------------  -----
0   c1      5 non-null      int64
1   c2      4 non-null      float64
2   c3      5 non-null      int64
dtypes: float64(1), int64(2)
memory usage: 248.0 bytes