日常用 Python 做数据分析最常用到的就是查询筛选了,按各种条件、各种维度以及组合挑出我们想要的数据,以方便我们分析挖掘。

东哥总结了日常查询和筛选常用的种骚操作,供各位学习参考。本文采用 sklearn boston 数据举例介绍。

from sklearn import datasets
import pandas as pd
boston = datasets.load_boston()
df = pd.DataFrame(boston.data, columns=boston.feature_names)

70.png

1. []

第一种是最快捷方便的,直接在dataframe的 [] 中写筛选的条件或者组合条件。比如下面,想要筛选出大于 NOX 这变量平均值的所有数据,然后按 NOX 降序排序。

df[df['NOX']>df['NOX'].mean()].sort_values(by='NOX',ascending=False).head()

71.png

当然,也可以使用组合条件,条件之间使用逻辑符号 & | 等。比如下面这个例子除了上面条件外再加上且条件 CHAS为1 ,注意逻辑符号分开的条件要用 () 隔开。

df[(df['NOX']>df['NOX'].mean())& (df['CHAS'] ==1)].sort_values(by='NOX',ascending=False).head()

72.png

2. loc/iloc

[] 之外, loc/iloc 应该是最常用的两种查询方法了。 loc 按标签值(列名和行索引取值)访问, iloc 按数字索引访问,均支持单值访问或切片查询。除了可以像 [] 按条件筛选数据以外, loc 还可以指定返回的列变量, 从行和列两个维度筛选。

比如下面这个例子,按条件筛选出数据,并筛选出指定变量,然后赋值。

df.loc[(df['NOX']>df['NOX'].mean()),['CHAS']] = 2

image.gif

3. isin

上面我们筛选条件 < > == != 都是个范围,但很多时候是需要锁定某些具体的值的,这时候就需要 isin 了。比如我们要限定 NOX 取值只能为 0.538,0.713,0.437 中时。

df.loc[df['NOX'].isin([0.538,0.713,0.437]),:].sample(5)

image.gif

当然,也可以做取反操作,在筛选条件前加 ~ 符号即可。

df.loc[~df['NOX'].isin([0.538,0.713,0.437]),:].sample(5)

73.png

4. str.contains

上面的举例都是 数值大小比较 的筛选条件,除数值以外当然也有 字符串的查询需求 pandas 里实现字符串的模糊筛选,可以用 .str.contains() 来实现,有点像在SQL语句里用的是 like

下面利用titanic的数据举例,筛选出人名中包含 Mrs 或者 Lily 的数据, | 或逻辑符号在引号内。

train.loc[train['Name'].str.contains('Mrs|Lily'),:].head()

74.png

.str.contains() 中还可以设置正则化筛选逻辑。

  • case=True:使用case指定区分大小写
  • na=True:就表示把有NAN的转换为布尔值True
  • flags=re.IGNORECASE:标志传递到re模块,例如re.IGNORECASE
  • regex=True:regex :如果为True,则假定第一个字符串是正则表达式,否则还是字符串


5. where/mask


在SQL里,我们知道 where 的功能是要把满足条件的筛选出来。pandas中 where 也是筛选,但用法稍有不同。

where 接受的条件需要是 布尔类型 的,如果不满足匹配条件,就被赋值为默认的 NaN 或其他指定值。举例如下,将 Sex male 当作筛选条件, cond 就是一列布尔型的Series,非male的值就都被赋值为默认的 NaN 空值了。

cond = train['Sex'] == 'male'
train['Sex'].where(cond, inplace=True)
train.head()

75.png

也可以用 other 赋给指定值。

cond = train['Sex'] == 'male'
train['Sex'].where(cond, other='FEMALE', inplace=True)

76.png

甚至还可以写组合条件。

train['quality'] = ''
traincond1 = train['Sex'] == 'male'
cond2 = train['Age'] > 25
train['quality'].where(cond1 & cond2, other='低质量男性', inplace=True)

77.png

mask where 是一对操作,与 where 正好反过来。

train['quality'].mask(cond1 & cond2, other='低质量男性', inplace=True)




    

image.gif 77.png


6. query


这是一种非常优雅的筛选数据方式。所有的筛选操作都在 '' 之内完成。

# 常用方式
train[train.Age > 25]
# query方式
train.query('Age > 25')

上面的两种方式效果上是一样的。再比如复杂点的,加入上面的 str.contains 用法的组合条件,注意条件里有 '' 时,两边要用 "" 包住。

train.query("Name.str.contains('William') & Age > 25")

image.gif

query 里还可以通过 @ 来设定变量。

name = 'William'
train.query("Name.str.contains(@name)")

78.png

7. filter


filter 是另外一个独特的筛选功能。 filter 不筛选具体数据,而是筛选特定的行或列。它支持三种筛选方式:

  • items:固定列名
  • regex:正则表达式
  • like:以及模糊查询
  • axis:控制是行index或列columns的查询

下面举例介绍下。


train.filter(items=['Age', 'Sex'])

79.png

train.filter(regex='S', axis=1) # 列名包含S的

80.png

train.filter(like='2', axis=0) # 索引中有2的

81.png

train.filter(regex='^2', axis=0).filter(like='S', axis=1)

82.png

8. any/all


any 方法意思是,如果至少有一个值为 True 结果便为 True all 需要所有值为 True 结果才为 True ,比如下面这样。


>> train['Cabin'].all()
>> False
>> train['Cabin'].any()
>> True

any all 一般是需要和其它操作配合使用的,比如查看每列的空值情况。

train.isnull().any(axis=0)

83.png

再比如查看含有空值的行数。

>>> train.isnull().any(axis=1).sum()
>>> 708



原创不易,欢迎点赞、留言、分享,支持我继续写下去。

在Pandas中通过时间频率来汇总数据的三种常用方法
当我们的数据涉及日期和时间时,分析随时间变化变得非常重要。Pandas提供了一种方便的方法,可以按不同的基于时间的间隔(如分钟、小时、天、周、月、季度或年)对时间序列数据进行分组。
pandas数据处理高级系列001-如何用一行代码优雅的删除一行数据中不包含特定字符串的行
pandas数据处理高级系列001-如何用一行代码优雅的删除一行数据中不包含特定字符串的行
Python库函数pandas读取excel数据
pandas 读取excel文件使用的是 read_excel方法。本文将详细解析read_excel方法的常用参数,以及实际的使用示例