Pandas入门实践2 -数据处理

news/2025/1/15 16:09:49/

为了准备数据进行分析,我们需要执行数据处理。在本节中,我们将学习如何清理和重新格式化数据(例如,重命名列和修复数据类型不匹配)、对其进行重构/整形,以及对其进行丰富(例如,离散化列、计算聚合和组合数据源)。

数据清洗

在本节中,我们将介绍如何创建、重命名和删除列;类型转换;和排序-所有这些都使我们的分析更容易。我们将使用NYC Open Data提供的2019年黄色出租车出行数据。

import pandas as pdtaxis = pd.read_csv('../data/2019_Yellow_Taxi_Trip_Data.csv')
taxis.head()

在这里插入图片描述

数据源:NYC Open Data

删除列
让我们从删除ID列和store_and_fwd_flag列开始,我们不会使用这些列。

mask = taxis.columns.str.contains('id$|store_and_fwd_flag', regex=True)
columns_to_drop = taxis.columns[mask]
columns_to_drop'''
Index(['vendorid', 'ratecodeid', 'store_and_fwd_flag', 'pulocationid','dolocationid'],dtype='object')
'''
taxis = taxis.drop(columns=columns_to_drop)
taxis.head()

在这里插入图片描述
提示:另一种方法是选择要保留的列:taxis.loc[:,~mask]

重命名列

taxis = taxis.rename(columns={'tpep_pickup_datetime': 'pickup', 'tpep_dropoff_datetime': 'dropoff'}
)
taxis.columns'''
Index(['pickup', 'dropoff', 'passenger_count', 'trip_distance', 'payment_type','fare_amount', 'extra', 'mta_tax', 'tip_amount', 'tolls_amount','improvement_surcharge', 'total_amount', 'congestion_surcharge'],dtype='object')
'''

类型转换
注意到数据类型有什么问题吗?

taxis.dtypes'''
pickup                    object
dropoff                   object
passenger_count            int64
trip_distance            float64
payment_type               int64
fare_amount              float64
extra                    float64
mta_tax                  float64
tip_amount               float64
tolls_amount             float64
improvement_surcharge    float64
total_amount             float64
congestion_surcharge     float64
dtype: object
'''

pickup 和 dropoff 都应存储为日期时间。让我们解决这个问题:

taxis[['pickup', 'dropoff']] = \taxis[['pickup', 'dropoff']].apply(pd.to_datetime)
taxis.dtypes'''
pickup                   datetime64[ns]
dropoff                  datetime64[ns]
passenger_count                   int64
trip_distance                   float64
payment_type                      int64
fare_amount                     float64
extra                           float64
mta_tax                         float64
tip_amount                      float64
tolls_amount                    float64
improvement_surcharge           float64
total_amount                    float64
congestion_surcharge            float64
dtype: object
'''

提示:还有其他方法可以执行类型转换。对于数值,我们可以使用pd.to_numeric()函数,稍后我们将看到astype()方法,这是一个更通用的方法。

创建新列
让我们为每一行计算以下内容:

  1. 行程时间
  2. 小费百分比
  3. 税金、通行费、规费及附加总额
  4. 出租车的平均速度
taxis = taxis.assign(elapsed_time=lambda x: x.dropoff - x.pickup, # 1cost_before_tip=lambda x: x.total_amount - x.tip_amount,tip_pct=lambda x: x.tip_amount / x.cost_before_tip, # 2fees=lambda x: x.cost_before_tip - x.fare_amount, # 3avg_speed=lambda x: x.trip_distance.div(x.elapsed_time.dt.total_seconds() / 60 / 60) # 4
)

我们的新列将添加到右侧:

taxis.head(2)

在这里插入图片描述
注意事项:
我们使用lambda函数是为了:1)避免重复输入taxis; 2)能够以创建cost_before_tip和elapsed_time列的相同方法访问它们。
要创建一个新列,我们也可以使用df['new_col'] = <values>

按值排序
我们可以使用sort_values()方法根据任意数量的列进行排序:

taxis.sort_values(['passenger_count', 'pickup'], ascending=[False, True]).head()

在这里插入图片描述
要挑选最大/最小的行,请使用nlargest()/nsmallest()。查看3个运行时间最长的行程:

taxis.nlargest(3, 'elapsed_time')

在这里插入图片描述

使用索引

到目前为止,我们还没有真正使用索引,因为它只是一个行号;然而,我们可以改变索引中的值来访问pandas的其他功能。

设置和排序索引
目前,我们有一个RangeIndex,但我们可以通过在调用set_index()时指定一个datetime列来切换到DatetimeIndex:

taxis = taxis.set_index('pickup')
taxis.head(3)

在这里插入图片描述
既然我们有一个完整数据集的样本,让我们按取件时间对索引进行排序:

taxis = taxis.sort_index()

提示:taxis.sort_index(axis=1)将按名称对列进行排序。轴参数在整个pandas中都存在:axis=0目标行,axis=1目标列。

现在我们可以根据日期时间从数据中选择范围,就像我们选择行号一样:

taxis['2019-10-23 07:45':'2019-10-23 08']

在这里插入图片描述
当不指定范围时,我们使用loc[]:

taxis.loc['2019-10-23 08']

在这里插入图片描述
重置索引
我们将在本节后面处理时间序列,但有时我们希望将索引重置为行号并恢复列。我们可以使用reset_index()方法:

taxis = taxis.reset_index()
taxis.head()

在这里插入图片描述

重塑数据

我们正在使用的出租车数据集是一种有利于分析的格式。但情况并非总是如此。现在我们来看一下TSA的旅客吞吐量数据,它将2021年的吞吐量与2020年和2019年的同一天进行了比较:

tsa = pd.read_csv('../data/tsa_passenger_throughput.csv', parse_dates=['Date'])
tsa.head()

在这里插入图片描述
数据源:TSA.gov

首先,我们将列名称小写,并将第一个单词(例如,2021年旅客吞吐量),以使其更易于处理:

tsa = tsa.rename(columns=lambda x: x.lower().split()[0])
tsa.head()

在这里插入图片描述
现在,我们可以重塑它。

Melting(熔化)
Melting(熔化)有助于将数据转换为长格式。现在,我们在一列中显示了所有的旅客吞吐量:

tsa_melted = tsa.melt(id_vars='date', # 唯一标识行的列(可以是多个)var_name='year', # 通过熔化创建的新列的名称value_name='travelers' # 包含来自已经融化列的值的新列的名称
)
tsa_melted.sample(5, random_state=1) # show some random entries

在这里插入图片描述
为了将其转换为旅客吞吐量的时间序列,我们需要将date列中的年份替换为year列中的年份。否则,我们就把往年的数字标错了年份。

tsa_melted = tsa_melted.assign(date=lambda x: pd.to_datetime(x.year + x.date.dt.strftime('-%m-%d'))
)
tsa_melted.sample(5, random_state=1)

在这里插入图片描述
这就留下了一些空值(数据集中不存在的日期):

tsa_melted.sort_values('date').tail(3)

在这里插入图片描述
可以使用dropna()方法删除这些内容:

tsa_melted = tsa_melted.dropna()
tsa_melted.sort_values('date').tail(3)

在这里插入图片描述
旋转
使用融合的数据,我们可以透视数据,以比较不同年份特定日期的TSA旅客吞吐量:

tsa_pivoted = tsa_melted\.query('date.dt.month == 3 and date.dt.day <= 10')\.assign(day_in_march=lambda x: x.date.dt.day)\.pivot(index='year', columns='day_in_march', values='travelers')
tsa_pivoted

在这里插入图片描述
重要提示:我们没有介绍unstack()和stack()方法,它们分别是透视和融化的附加方法。
当我们有一个多层次的索引时,这些就派上用场了(例如,如果我们对多列运行set_index())

转置

tsa_pivoted.T

在这里插入图片描述
合并

我们通常会在假期前后观察航空旅行的变化,因此在TSA数据集中添加有关日期的信息可以提供更多上下文。holidays.csv文件包含美国的几个主要节日:

holidays = pd.read_csv('../data/holidays.csv', parse_dates=True, index_col='date')
holidays.loc['2019']

在这里插入图片描述
将假日与TSA旅客吞吐量数据合并将为我们的分析提供更多背景:

tsa_melted_holidays = tsa_melted\.merge(holidays, left_on='date', right_index=True, how='left')\.sort_values('date')
tsa_melted_holidays.head()

在这里插入图片描述
提示:这个方法有很多参数,所以一定要查阅文档。要追加行,请查看pd.concat()函数。

我们可以更进一步,把每个假期的前后几天标记为假期的一部分。这将更容易比较跨年的假日旅行,并寻找假日前后旅行的任何上升:

tsa_melted_holiday_travel = tsa_melted_holidays.assign(holiday=lambda x:x.holiday\.fillna(method='ffill', limit=1)\.fillna(method='bfill', limit=2)
)

提示:查看文档以获得fillna()方法可用功能的完整列表。

请注意,我们现在有了每个假日后一天和前两天的值。2019年的感恩节是11月28日,所以26日、27日、29日都排满了。因为我们只替换空值,所以我们不会用平安夜的前向填充覆盖Christmas Day:

tsa_melted_holiday_travel.query('year == "2019" and ''(holiday == "Thanksgiving" or holiday.str.contains("Christmas"))'
)

在这里插入图片描述

聚合和分组

在重塑和清理数据之后,我们可以执行聚合,以各种方式汇总数据。在本节中,我们将探索如何使用透视表、交叉表和分组依据操作来聚合数据。

数据透视表

我们可以构建一个透视表来比较数据集中各年的假日旅行情况:

tsa_melted_holiday_travel.pivot_table(index='year', columns='holiday', values='travelers', aggfunc='sum'
)

在这里插入图片描述
我们可以在这个结果上使用pct_change()方法来查看哪些假日旅行时段的旅行变化最大:

tsa_melted_holiday_travel.pivot_table(index='year', columns='holiday', values='travelers', aggfunc='sum'
).pct_change()

在这里插入图片描述
让我们创建最后一个包含列和行小计的透视表,沿着对格式进行一些改进。首先,我们为所有浮动设置一个显示选项:

pd.set_option('display.float_format', '{:,.0f}'.format)

接下来,我们将圣诞前夜和圣诞节分组在一起,同样,将新年前夜和元旦分组在一起,并创建透视表:

import numpy as nptsa_melted_holiday_travel.assign(holiday=lambda x: np.where(x.holiday.str.contains('Christmas|New Year', regex=True), x.holiday.str.replace('Day|Eve', '', regex=True).str.strip(), x.holiday)
).pivot_table(index='year', columns='holiday', values='travelers', aggfunc='sum', margins=True, margins_name='Total'
)

在这里插入图片描述
在继续之前,让我们重置显示选项:

pd.reset_option('display.float_format')

时间序列

在处理时间序列数据时,pandas为我们提供了额外的功能,不仅可以比较数据集中的观测结果,还可以利用它们在时间上的关系来分析数据。在本节中,我们将看到一些这样的操作,用于选择日期/时间范围、计算随时间的变化、执行窗口计算以及将数据重新采样到不同的日期/时间间隔。

根据日期和时间选择

taxis = taxis.set_index('dropoff').sort_index()

我们前面看到可以对日期时间进行切片:

taxis['2019-10-24 12':'2019-10-24 13']

在这里插入图片描述
我们也可以用简写来表示这个范围。注意我们必须在这里使用loc[]:

taxis.loc['2019-10-24 12']

在这里插入图片描述
我们可以使用between_time()方法提取任意一天某个特定时间范围内发生的下降:

taxis.between_time('12:00', '13:00')

在这里插入图片描述
提示:at_time()方法可用于提取给定时间的所有条目(e.g., 12:35:27)。

最后,head()和tail()将我们限制在一定数量的行,但是我们可能对数据的前/后2小时(或任何其他时间间隔)内的行感兴趣,在这种情况下,我们应该使用first()/ last():

taxis.first('2H')

在这里插入图片描述
在本节的其余部分,我们将使用TSA旅客吞吐量数据。让我们从设置date列的索引开始:

tsa_melted_holiday_travel = tsa_melted_holiday_travel.set_index('date')

计算随时间的变化

tsa_melted_holiday_travel.loc['2020'].assign(one_day_change=lambda x: x.travelers.diff(),seven_day_change=lambda x: x.travelers.diff(7),
).head(10)

在这里插入图片描述
提示:要执行减法以外的运算,请查看shift()方法。它还使跨列执行操作成为可能。

重采样

我们可以使用重采样将时间序列数据聚合到一个新的频率:

tsa_melted_holiday_travel['2019':'2021-Q1'].select_dtypes(include='number')\.resample('Q').agg(['sum', 'mean', 'std'])

在这里插入图片描述
窗口计算

窗口计算类似于分组依据计算,不同之处在于执行计算的组不是静态的-它可以移动或扩展。Pandas提供用于构造各种窗口的功能,包括移动/滚动窗口,展开窗口(例如,在时间序列中直到当前日期的累积和或平均值),以及指数加权移动窗口(对更近的观测值比更远的观测值更加权)。这里我们只看滚动和展开计算。

执行窗口计算与按计算分组非常相似-我们首先定义窗口,然后指定聚合:

tsa_melted_holiday_travel.loc['2020'].assign(**{'7D MA': lambda x: x.rolling('7D').travelers.mean(),'YTD mean': lambda x: x.expanding().travelers.mean()}
).head(10)

在这里插入图片描述
要想了解到底发生了什么,最好把原始数据和结果可视化,下面我们就来先睹为快,用pandas绘图。首先,在notebook中嵌入SVG格式图的一些设置:

import matplotlib_inline
from utils import mpl_svg_configmatplotlib_inline.backend_inline.set_matplotlib_formats('svg', # output images using SVG format**mpl_svg_config('section-2') # optional: configure metadata
)

现在,我们调用plot()方法来可视化数据:

_ = tsa_melted_holiday_travel.loc['2020'].assign(**{'7D MA': lambda x: x.rolling('7D').travelers.mean(),'YTD mean': lambda x: x.expanding().travelers.mean()}
).plot(title='2020 TSA Traveler Throughput', ylabel='travelers', alpha=0.8)

在这里插入图片描述


http://www.ppmy.cn/news/47526.html

相关文章

Laravel使用JWT

开始安装jwt &#xff08;本次安装不建议直接在项目中安装及使用&#xff09; 1.composer 安装jwt composer require tymon/jwt-auth 1.0.0-rc.1 2.在config 文件夹的app.php 中注册服务提供者 providers > [Tymon\JWTAuth\Providers\LaravelServiceProvider::class, ]…

使用计算机视觉实战项目精通 OpenCV:6~8

原文&#xff1a;Mastering OpenCV with Practical Computer Vision Projects 协议&#xff1a;CC BY-NC-SA 4.0 译者&#xff1a;飞龙 本文来自【ApacheCN 计算机视觉 译文集】&#xff0c;采用译后编辑&#xff08;MTPE&#xff09;流程来尽可能提升效率。 当别人说你没有底线…

01、Cadence使用记录之新建工程与基础操作(原理图绘制:OrCAD Capture CIS)

01、Cadence使用记录之新建工程与基础操作&#xff08;原理图绘制&#xff1a;OrCAD Capture CIS&#xff09; 硕士学电磁场去了&#xff0c;写点博客记录下学习过程。 参考的教程是B站的视频&#xff1a;allegro软件入门视频教程全集100讲 本科的时候就对Cadence有所耳闻&am…

docker问题集锦

1.http: server gave HTTP response to HTTPS client sudo vim /etc/docker/daemon.json 添加{“insecure-registries”: [“ip:端口”]} sudo service docker restart 无效 sudo vim /lib/systemd/system/docker.service 在ExecStart最后添加 --insecure-registry ip:端口 sud…

GDB调试实验

一、实验准备 在 Linux 环境软件开发中&#xff0c;GDB 是调试 C 和 C 程序的主要工具。本次实验围绕着GDB常用的调试操作进行。 1、设置断点的意义 当我们想查看变量内容&#xff0c;堆栈情况等等&#xff0c;可以指定断点。程序执行到断点处会暂停执行。break 命令用来设置…

亚马逊、ebay、temu如何提升产品点击率?测评自养号解析

产品点击率对于店铺销售额的影响至关重要&#xff0c;尤其是在竞争越来越激烈的市场环境中&#xff0c;想要有销量和转化&#xff0c;提高产品listing点击率成为了非常关键的一环。 1. 产品主图 顾客浏览产品时&#xff0c;第一眼看到的就是主图&#xff0c;一张优质的主图更容…

什么是MVVM?

MVVM 是 Model-View-ViewModel 的缩写&#xff0c;是M-V-VM三部分组成。它本质上就是MVC的改进版。 M&#xff1a;Model 代表数据模型&#xff0c;也可以在Model中定义数据修改和操作的业务逻辑。 V&#xff1a;View 代表视图UI&#xff0c;它负责将数据模型转化成UI 展现出来。…

材料科学基础学习指导-吕宇鹏-名词和术语解释-第5章:相图

目录 第一部分 第二部分​​​​​​​ 第三部分 第四部分​ 第一部分 1.1组元&#xff1a;是材料科学中的基本术语。意思是组成合金的独立的、最基本的单元。 1.2相&#xff1a; 指合金中具有同一聚集状态、同一晶体结构和性质并以界面相互隔开的均匀组成部分。​​​​…