目录
1. 判断缺失值位置、数量
data[data['filled'].isnull().values == True]#判断缺失值的位置
b = data[data.isna().any(axis=1)]
data.dropna()等价于data[data.notnall()]
data.isnull().sum()#各列的缺失值数量;
data.isnull().sum().sum()#总体null的数量。
online.isnull().sum().sort_values(ascending=False)
2. 数据插补
#数据插补:优先从左边进行插入
data = data.iloc[:,2:-1]
data = data.fillna(method='ffill',axis=1) # 同行,从左往右补全
data = data.fillna(method='bfill',axis=1) # 同列,从右往左补
data = data.interpolate(limit_direction='forward',axis=1) # 时间顺序插值
data= data.interpolate(limit_direction='backward',axis=1) # 时间顺序插值
2.1 interpolate()插补
import pandas as pd
import numpy as np
data = pd.Series([1,2,3,np.nan,np.nan,6,np.nan])
data
0 1.0
1 2.0
2 3.0
3 NaN
4 NaN
5 6.0
6 NaN
dtype: float64
不设置任何参数
data.interpolate()
0 1.0
1 2.0
2 3.0
3 4.0
4 5.0
5 6.0
6 6.0
dtype: float64
使用‘pad’方法,limit设置为1
data.interpolate(method='pad', limit=1)
0 1.0
1 2.0
2 3.0
3 3.0
4 NaN
5 6.0
6 6.0
dtype: float64
2.2 interpolate()参数介绍
DataFrame.interpolate(method=‘linear’, axis=0, limit=None, inplace=False, limit_direction=None, limit_area=None, downcast=None, **kwargs)
-
method : str,默认为‘linear’使用插值方法。
可用的插值方法:- ‘linear’:忽略索引,线性等距插值。这是MultiIndexes支持的唯一方法。
- ‘time’: 在以天或者更高频率的数据上插入给定的时间间隔长度数据。
- ‘index’, ‘values’: 使用索引的实际数值。
- ‘pad’:使用现有值填写NaN。
- ‘nearest’, ‘zero’, ‘slinear’, ‘quadratic’, ‘cubic’, ‘spline’, ‘barycentric’, ‘polynomial’: 传递给 scipy.interpolate.interp1d。这些方法使用索引的数值。‘polynomial’ 和 ‘spline’ 都要求您还指定一个顺序(int),例如 ,df.interpolate(method=‘polynomial’, order=5)
- ‘krogh’,‘piecewise_polynomial’,‘spline’,‘pchip’,‘akima’:包括类似名称的SciPy插值方法。
- ‘from_derivatives’:指 scipy.interpolate.BPoly.from_derivatives,它替换了scipy 0.18中的’piecewise_polynomial’插值方法。
-
axis : {0或’index’,1或’columns’,None},默认为None;沿轴进行interpolate。
-
limit: int;要填充的连续NaN的最大数量。必须大于0。
-
inplace : bool,默认为False;如果可以,更新现有数据。
-
limit_direction : {‘forward’,‘backward’,‘both’},默认为’forward’;如果指定了限制,则将沿该方向填充连续的NaN。
-
limit_area : {None, ‘inside’, ‘outside’}, 默认为None;如果指定了限制,则连续的NaN将填充此限制。
None:无填充限制。- ‘inside’:仅填充有效值包围的NaN。
- ‘outside’: 仅在有效值之外填充NaN。
2.3 范例
采用interpolate()函数使用线性方法向后插值缺失值
df = pd.DataFrame([(0.0, np.nan, -1.0, 1.0),
(np.nan, 2.0, np.nan, np.nan),
(2.0, 3.0, np.nan, 9.0),
(np.nan, 4.0, -4.0, 16.0)],
columns=list('abcd'))
print(df)
输出结果:
df.interpolate(method='linear', limit_direction='backward', axis=0)
输出结果:
最后一行中的值无法填充,因为值的填充方向为 backward 并且没有可用于插值的后续值。
3. 删除缺失值
dropna(thresh=n) # 简单的理解:这一行除去NA值,剩余数值的数量大于等于n,便显示这一行。
data.dropna(how = 'all') # 传入这个参数后将只丢弃全为缺失值的那些行
data.dropna(axis = 1) # 丢弃有缺失值的列(一般不会这么做,这样会删掉一个特征)
data.dropna(axis=1,how="all") # 丢弃全为缺失值的那些列
data.dropna(axis=0,subset= ["Age", "Sex"]) #丢弃‘Age’和‘Sex’这两列中有缺失值的行
In [38]: pd.isnull(idx)
Out[38]: array([False, False, True], dtype=bool)
pandas.dropna() how参数当我们至少有一个NA时,确定是否从DataFrame中删除行或列
how='all’或者how=‘any’。
how='all’时表示删除全是缺失值的行(列)
how='any’时表示删除只要含有缺失值的行(列)
4. 缺失值处理:骚操作
有这么一个情形,要处理pandas.DataFrame表格数据,如下图所示,value 这一列有很多连续的空值,空值处理需求如下:
- 连续空值行数超过10次的行全部按行删掉;
- 连续空值行数小于等于10次的,则取上一个实数值和下一个实数值的均值来补全。
试问该怎么做?
答案:
NUM_NAN = 10
nan_r, _ = np.where(np.isnan(df)) # 找到所有NaN的值位置,nan_r表示行标,占位符_表示列标
# 统计哪一块数据应该删除
nan_list = [] # 只收集连续空值超过NUM_NAN个数的行索引
fun = lambda x: x[1] - x[0]
for k, g in groupby(enumerate(nan_r), fun):
find_list = [j for i, j in g] # 连续数字的列表
if len(find_list) > NUM_NAN: # 时间连续的点超过NUM_NAN个就删掉
nan_list = nan_list + find_list
# 存较大片的缺省值,进行删除
if len(nan_list) != 0:
df = df.reset_index()
df = df.drop(nan_list)
df = df.set_index(df['time'])
df = df.drop(['time'], axis=1)
# 缺省值取前一行和后一行的均值
df = (df.fillna(method='backfill') + df.fillna(method='pad')) / 2
df.to_csv('test.csv')
5. notna()函数删除某列中含有空值的行
import pandas as pd
data = pd.read_excel('test.xlsx',sheet_name='Sheet1')
datanota = data[data['销售人员'].notna()]
print(datanota)
输出结果:
D:\Python\Anaconda\python.exe D:/Python/test/EASdeal/test.py
城市 销售金额 销售人员
0 北京 10000 张丽丽
1 上海 50000 潇潇
2 深圳 60000 笨笨笨
3 成都 40000 达达
Process finished with exit code 0
6. 筛选存在空值的行or非空值的行
import pandas as pd
test = pd.read_excel('D:/pp/test_null.xlsx','Sheet1');
test
6.1 筛选任意列有空值的行
test[test.isnull().T.any()] #无论哪列,有空值的被选出来
6.2 指定列有空值的行
test[test[['生日']].isnull().T.any()] #只选择【生日】列有空值的所有行
6.3 去掉指定属性存在空值的行
test = test[test['性别'].notna()] #去掉【性别】为空值的行
test
参考链接:
[1] python数据分析之清洗数据:缺失值处理 2020.2