Pandas 2.2 中文官方教程和指南(三)(1)

简介: Pandas 2.2 中文官方教程和指南(三)

如何操作文本数据

原文:pandas.pydata.org/docs/getting_started/intro_tutorials/10_text_data.html

  • 将所有名称字符改为小写。
In [4]: titanic["Name"].str.lower()
Out[4]: 
0                                braund, mr. owen harris
1      cumings, mrs. john bradley (florence briggs th...
2                                 heikkinen, miss. laina
3           futrelle, mrs. jacques heath (lily may peel)
4                               allen, mr. william henry
 ... 
886                                montvila, rev. juozas
887                         graham, miss. margaret edith
888             johnston, miss. catherine helen "carrie"
889                                behr, mr. karl howell
890                                  dooley, mr. patrick
Name: Name, Length: 891, dtype: object 
  • 要使Name列中的每个字符串都变为小写,选择Name列(参见数据选择教程),添加str访问器并应用lower方法。因此,每个字符串都被逐个转换。

时间序列教程中具有dt访问器的日期时间对象类似,在使用str访问器时可以使用许多专门的字符串方法。这些方法通常与单个元素的内置字符串方法具有匹配的名称,但是在每个值的列上逐个应用(记得逐元素计算吗?)。

  • 创建一个新列Surname,其中包含乘客的姓氏,通过提取逗号前的部分。
In [5]: titanic["Name"].str.split(",")
Out[5]: 
0                             [Braund,  Mr. Owen Harris]
1      [Cumings,  Mrs. John Bradley (Florence Briggs ...
2                              [Heikkinen,  Miss. Laina]
3        [Futrelle,  Mrs. Jacques Heath (Lily May Peel)]
4                            [Allen,  Mr. William Henry]
 ... 
886                             [Montvila,  Rev. Juozas]
887                      [Graham,  Miss. Margaret Edith]
888          [Johnston,  Miss. Catherine Helen "Carrie"]
889                             [Behr,  Mr. Karl Howell]
890                               [Dooley,  Mr. Patrick]
Name: Name, Length: 891, dtype: object 
  • 使用Series.str.split()方法,每个值都返回一个包含 2 个元素的列表。第一个元素是逗号前的部分,第二个元素是逗号后的部分。
In [6]: titanic["Surname"] = titanic["Name"].str.split(",").str.get(0)
In [7]: titanic["Surname"]
Out[7]: 
0         Braund
1        Cumings
2      Heikkinen
3       Futrelle
4          Allen
 ... 
886     Montvila
887       Graham
888     Johnston
889         Behr
890       Dooley
Name: Surname, Length: 891, dtype: object 
  • 由于我们只对代表姓氏的第一部分感兴趣(元素 0),我们可以再次使用str访问器,并应用Series.str.get()来提取相关部分。事实上,这些字符串函数可以连接起来组合多个函数!

到用户指南

有关提取字符串部分的更多信息,请参阅用户指南中关于拆分和替换字符串的部分。

  • 提取关于泰坦尼克号上女伯爵的乘客数据。
In [8]: titanic["Name"].str.contains("Countess")
Out[8]: 
0      False
1      False
2      False
3      False
4      False
 ... 
886    False
887    False
888    False
889    False
890    False
Name: Name, Length: 891, dtype: bool 
In [9]: titanic[titanic["Name"].str.contains("Countess")]
Out[9]: 
 PassengerId  Survived  Pclass  ... Cabin Embarked  Surname
759          760         1       1  ...   B77        S   Rothes
[1 rows x 13 columns] 
  • (对她的故事感兴趣吗?请参阅 维基百科)
    字符串方法Series.str.contains()检查列Name中的每个值是否包含单词Countess,并对每个值返回TrueCountess是名称的一部分)或FalseCountess不是名称的一部分)。此输出可用于使用在数据子集教程中介绍的条件(布尔)索引来对数据进行子选择。由于泰坦尼克号上只有一位女伯爵,我们得到一行作为结果。

注意

字符串的更强大的提取操作是支持的,因为Series.str.contains()Series.str.extract() 方法接受正则表达式,但不在本教程的范围内。

到用户指南

更多有关提取字符串部分的信息,请参阅用户指南中有关字符串匹配和提取的部分。

  • 泰坦尼克号的乘客中,哪位乘客的名字最长?
In [10]: titanic["Name"].str.len()
Out[10]: 
0      23
1      51
2      22
3      44
4      24
 ..
886    21
887    28
888    40
889    21
890    19
Name: Name, Length: 891, dtype: int64 
  • 要获得最长的名称,我们首先必须获取Name列中每个名称的长度。通过使用 pandas 字符串方法,对每个名称单独应用Series.str.len()函数(逐元素)。
In [11]: titanic["Name"].str.len().idxmax()
Out[11]: 307 
  • 接下来,我们需要获取对应位置,最好是表格中名字长度最大的索引标签。 idxmax() 方法正是这样做的。它不是字符串方法,适用于整数,因此不使用str
In [12]: titanic.loc[titanic["Name"].str.len().idxmax(), "Name"]
Out[12]: 'Penasco y Castellana, Mrs. Victor de Satode (Maria Josefa Perez de Soto y Vallejo)' 
  • 基于行的索引名称(307)和列的名称(Name),我们可以使用loc运算符进行选择,该运算符在子集切片教程中介绍过。
  • 在“性别”列中,将“male”的值替换为“M”,将“female”的值替换为“F”。
In [13]: titanic["Sex_short"] = titanic["Sex"].replace({"male": "M", "female": "F"})
In [14]: titanic["Sex_short"]
Out[14]: 
0      M
1      F
2      F
3      F
4      M
 ..
886    M
887    F
888    F
889    M
890    M
Name: Sex_short, Length: 891, dtype: object 
  • replace() 不是一个字符串方法,它提供了一种方便的方式来使用映射或词汇表来转换某些值。它需要一个dictionary来定义映射 {from : to}

警告

还有一个可用的replace()方法,可以替换特定的字符集。但是,当有多个值的映射时,这将变得:

titanic["Sex_short"] = titanic["Sex"].str.replace("female", "F")
titanic["Sex_short"] = titanic["Sex_short"].str.replace("male", "M") 

这将变得繁琐,并且很容易出错。想想(或者试试)如果这两个语句以相反的顺序应用会发生什么…

记住
  • 可以使用str访问器使用字符串方法。
  • 字符串方法是逐元素进行的,可以用于条件索引。
  • replace方法是根据给定字典转换值的便捷方法。

到用户指南

用户指南页面提供了处理文本数据的全面概述。

与其他工具的比较

原文:pandas.pydata.org/docs/getting_started/comparison/index.html

  • 与 R / R 库的比较
  • 快速参考
  • 基本 R
  • plyr
  • reshape / reshape2
  • 与 SQL 的比较
  • 复制 vs. 原地操作
  • 选择
  • WHERE
  • GROUP BY
  • 连接
  • UNION
  • 限制
  • pandas 对一些 SQL 分析和聚合函数的等效操作
  • 更新
  • 删除
  • 与电子表格的比较
  • 数据结构
  • 数据输入/输出
  • 数据操作
  • 字符串处理
  • 合并
  • 其他考虑因素
  • 与 SAS 的比较
  • 数据结构
  • 数据输入/输出
  • 数据操作
  • 字符串处理
  • 合并
  • 缺失数据
  • GroupBy
  • 其他考虑因素
  • 与 Stata 的比较
  • 数据结构
  • 数据输入/输出
  • 数据操作
  • 字符串处理
  • 合并
  • 缺失数据
  • GroupBy
  • 其他考虑因素

与 R/R 库的比较

译文:pandas.pydata.org/docs/getting_started/comparison/comparison_with_r.html

由于 pandas 旨在提供许多人们使用R的数据操作和分析功能,因此本页面旨在更详细地查看R 语言及其许多第三方库与 pandas 的关系。在与 R 和 CRAN 库的比较中,我们关心以下几点:

  • 功能性/灵活性:每个工具可以/不可以做什么
  • 性能:操作有多快。最好提供硬性数据/基准
  • 易用性:一个工具更容易/更难使用(您可能需要通过并排代码比较来判断)

本页面还提供了一个为这些 R 包的用户提供一点翻译指南的页面。

快速参考

我们将从一个快速参考指南开始,将一些常见的 R 操作(使用dplyr)与 pandas 的等效操作进行配对。

查询、过滤、抽样

R pandas
dim(df) df.shape
head(df) df.head()
slice(df, 1:10) df.iloc[:9]
filter(df, col1 == 1, col2 == 1) df.query('col1 == 1 & col2 == 1')
df[df$col1 == 1 & df$col2 == 1,] df[(df.col1 == 1) & (df.col2 == 1)]
select(df, col1, col2) df[['col1', 'col2']]
select(df, col1:col3) df.loc[:, 'col1':'col3']
select(df, -(col1:col3)) df.drop(cols_to_drop, axis=1) 但请参见[1]
distinct(select(df, col1)) df[['col1']].drop_duplicates()
distinct(select(df, col1, col2)) df[['col1', 'col2']].drop_duplicates()
sample_n(df, 10) df.sample(n=10)
sample_frac(df, 0.01) df.sample(frac=0.01)

排序

R pandas
arrange(df, col1, col2) df.sort_values(['col1', 'col2'])
arrange(df, desc(col1)) df.sort_values('col1', ascending=False)

转换

R pandas
select(df, col_one = col1) df.rename(columns={'col1': 'col_one'})['col_one']
rename(df, col_one = col1) df.rename(columns={'col1': 'col_one'})
mutate(df, c=a-b) df.assign(c=df['a']-df['b'])

分组和汇总

R pandas
summary(df) df.describe()
gdf <- group_by(df, col1) gdf = df.groupby('col1')
summarise(gdf, avg=mean(col1, na.rm=TRUE)) df.groupby('col1').agg({'col1': 'mean'})
summarise(gdf, total=sum(col1)) df.groupby('col1').sum()

基础 R

使用 R 的c进行切片

R 使得通过名称轻松访问 data.frame 列成为可能

df  <-  data.frame(a=rnorm(5),  b=rnorm(5),  c=rnorm(5),  d=rnorm(5),  e=rnorm(5))
df[,  c("a",  "c",  "e")] 

或按整数位置

df  <-  data.frame(matrix(rnorm(1000),  ncol=100))
df[,  c(1:10,  25:30,  40,  50:100)] 

在 pandas 中按名称选择多列很简单

In [1]: df = pd.DataFrame(np.random.randn(10, 3), columns=list("abc"))
In [2]: df[["a", "c"]]
Out[2]: 
 a         c
0  0.469112 -1.509059
1 -1.135632 -0.173215
2  0.119209 -0.861849
3 -2.104569  1.071804
4  0.721555 -1.039575
5  0.271860  0.567020
6  0.276232 -0.673690
7  0.113648  0.524988
8  0.404705 -1.715002
9 -1.039268 -1.157892
In [3]: df.loc[:, ["a", "c"]]
Out[3]: 
 a         c
0  0.469112 -1.509059
1 -1.135632 -0.173215
2  0.119209 -0.861849
3 -2.104569  1.071804
4  0.721555 -1.039575
5  0.271860  0.567020
6  0.276232 -0.673690
7  0.113648  0.524988
8  0.404705 -1.715002
9 -1.039268 -1.157892 

通过整数位置选择多个不连续列可以通过iloc索引器属性和numpy.r_的组合实现。

In [4]: named = list("abcdefg")
In [5]: n = 30
In [6]: columns = named + np.arange(len(named), n).tolist()
In [7]: df = pd.DataFrame(np.random.randn(n, n), columns=columns)
In [8]: df.iloc[:, np.r_[:10, 24:30]]
Out[8]: 
 a         b         c  ...        27        28        29
0  -1.344312  0.844885  1.075770  ...  0.813850  0.132003 -0.827317
1  -0.076467 -1.187678  1.130127  ...  0.149748 -0.732339  0.687738
2   0.176444  0.403310 -0.154951  ... -0.493662  0.600178  0.274230
3   0.132885 -0.023688  2.410179  ...  0.109121  1.126203 -0.977349
4   1.474071 -0.064034 -1.282782  ... -0.858447  0.306996 -0.028665
..       ...       ...       ...  ...       ...       ...       ...
25  1.492125 -0.068190  0.681456  ...  0.428572  0.880609  0.487645
26  0.725238  0.624607 -0.141185  ...  1.008500  1.424017  0.717110
27  1.262419  1.950057  0.301038  ...  1.007824  2.826008  1.458383
28 -1.585746 -0.899734  0.921494  ...  0.577223 -1.088417  0.326687
29 -0.986248  0.169729 -1.158091  ... -2.013086 -1.602549  0.333109
[30 rows x 16 columns] 

aggregate

在 R 中,您可能希望将数据拆分为子集并为每个子集计算平均值。使用名为df的数据框,并将其拆分为by1by2组:

df  <-  data.frame(
  v1  =  c(1,3,5,7,8,3,5,NA,4,5,7,9),
  v2  =  c(11,33,55,77,88,33,55,NA,44,55,77,99),
  by1  =  c("red",  "blue",  1,  2,  NA,  "big",  1,  2,  "red",  1,  NA,  12),
  by2  =  c("wet",  "dry",  99,  95,  NA,  "damp",  95,  99,  "red",  99,  NA,  NA))
aggregate(x=df[,  c("v1",  "v2")],  by=list(mydf2$by1,  mydf2$by2),  FUN  =  mean) 

groupby()方法类似于基本的 R aggregate函数。

In [9]: df = pd.DataFrame(
 ...:    {
 ...:        "v1": [1, 3, 5, 7, 8, 3, 5, np.nan, 4, 5, 7, 9],
 ...:        "v2": [11, 33, 55, 77, 88, 33, 55, np.nan, 44, 55, 77, 99],
 ...:        "by1": ["red", "blue", 1, 2, np.nan, "big", 1, 2, "red", 1, np.nan, 12],
 ...:        "by2": [
 ...:            "wet",
 ...:            "dry",
 ...:            99,
 ...:            95,
 ...:            np.nan,
 ...:            "damp",
 ...:            95,
 ...:            99,
 ...:            "red",
 ...:            99,
 ...:            np.nan,
 ...:            np.nan,
 ...:        ],
 ...:    }
 ...: )
 ...: 
In [10]: g = df.groupby(["by1", "by2"])
In [11]: g[["v1", "v2"]].mean()
Out[11]: 
 v1    v2
by1  by2 
1    95    5.0  55.0
 99    5.0  55.0
2    95    7.0  77.0
 99    NaN   NaN
big  damp  3.0  33.0
blue dry   3.0  33.0
red  red   4.0  44.0
 wet   1.0  11.0 

有关更多详细信息和示例,请参阅分组文档。

match / %in%

在 R 中选择数据的常见方法是使用%in%,该运算符使用函数match定义。运算符%in%用于返回指示是否存在匹配项的逻辑向量:

s  <-  0:4
s  %in%  c(2,4) 

isin()方法类似于 R 的%in%运算符:

In [12]: s = pd.Series(np.arange(5), dtype=np.float32)
In [13]: s.isin([2, 4])
Out[13]: 
0    False
1    False
2     True
3    False
4     True
dtype: bool 

match函数返回其第一个参数在第二个参数中匹配位置的向量:

s  <-  0:4
match(s,  c(2,4)) 

有关更多详细信息和示例,请参阅重塑文档。

tapply

tapply类似于aggregate,但数据可以是不规则的数组,因为子类大小可能不规则。使用名为baseball的数据框,并根据数组team检索信息:

baseball  <-
  data.frame(team  =  gl(5,  5,
  labels  =  paste("Team",  LETTERS[1:5])),
  player  =  sample(letters,  25),
  batting.average  =  runif(25,  .200,  .400))
tapply(baseball$batting.average,  baseball.example$team,
  max) 

在 pandas 中,我们可以使用pivot_table()方法来处理这个问题:

In [14]: import random
In [15]: import string
In [16]: baseball = pd.DataFrame(
 ....:    {
 ....:        "team": ["team %d" % (x + 1) for x in range(5)] * 5,
 ....:        "player": random.sample(list(string.ascii_lowercase), 25),
 ....:        "batting avg": np.random.uniform(0.200, 0.400, 25),
 ....:    }
 ....: )
 ....: 
In [17]: baseball.pivot_table(values="batting avg", columns="team", aggfunc="max")
Out[17]: 
team           team 1    team 2    team 3    team 4    team 5
batting avg  0.352134  0.295327  0.397191  0.394457  0.396194 

有关更多详细信息和示例,请参阅重塑文档。

subset

query()方法类似于基本的 R subset函数。在 R 中,您可能希望获取data.frame的行,其中一列的值小于另一列的值:

df  <-  data.frame(a=rnorm(10),  b=rnorm(10))
subset(df,  a  <=  b)
df[df$a  <=  df$b,]  # note the comma 

在 pandas 中,有几种方法可以执行子集。您可以使用query()或将表达式传递为索引/切片,以及标准布尔索引:

In [18]: df = pd.DataFrame({"a": np.random.randn(10), "b": np.random.randn(10)})
In [19]: df.query("a <= b")
Out[19]: 
 a         b
1  0.174950  0.552887
2 -0.023167  0.148084
3 -0.495291 -0.300218
4 -0.860736  0.197378
5 -1.134146  1.720780
7 -0.290098  0.083515
8  0.238636  0.946550
In [20]: df[df["a"] <= df["b"]]
Out[20]: 
 a         b
1  0.174950  0.552887
2 -0.023167  0.148084
3 -0.495291 -0.300218
4 -0.860736  0.197378
5 -1.134146  1.720780
7 -0.290098  0.083515
8  0.238636  0.946550
In [21]: df.loc[df["a"] <= df["b"]]
Out[21]: 
 a         b
1  0.174950  0.552887
2 -0.023167  0.148084
3 -0.495291 -0.300218
4 -0.860736  0.197378
5 -1.134146  1.720780
7 -0.290098  0.083515
8  0.238636  0.946550 

有关更多详细信息和示例,请参阅查询文档。

with

在 R 中使用名为df的数据框,其中包含ab列的表达式将使用with进行评估:

df  <-  data.frame(a=rnorm(10),  b=rnorm(10))
with(df,  a  +  b)
df$a  +  df$b  # same as the previous expression 

在 pandas 中,使用eval()方法的等效表达式将是:

In [22]: df = pd.DataFrame({"a": np.random.randn(10), "b": np.random.randn(10)})
In [23]: df.eval("a + b")
Out[23]: 
0   -0.091430
1   -2.483890
2   -0.252728
3   -0.626444
4   -0.261740
5    2.149503
6   -0.332214
7    0.799331
8   -2.377245
9    2.104677
dtype: float64
In [24]: df["a"] + df["b"]  # same as the previous expression
Out[24]: 
0   -0.091430
1   -2.483890
2   -0.252728
3   -0.626444
4   -0.261740
5    2.149503
6   -0.332214
7    0.799331
8   -2.377245
9    2.104677
dtype: float64 

在某些情况下,eval() 比纯 Python 中的评估要快得多。更多详细信息和示例请参见 eval 文档。


Pandas 2.2 中文官方教程和指南(三)(2)https://developer.aliyun.com/article/1509763

相关文章
|
10月前
|
SQL 数据采集 数据挖掘
Pandas 教程
10月更文挑战第25天
214 2
|
存储 JSON 数据格式
Pandas 使用教程 CSV - CSV 转 JSON
Pandas 使用教程 CSV - CSV 转 JSON
126 0
|
JSON 数据格式 Python
Pandas 使用教程 JSON
Pandas 使用教程 JSON
143 0
|
SQL 数据采集 JSON
Pandas 使用教程 Series、DataFrame
Pandas 使用教程 Series、DataFrame
226 0
|
数据采集 存储 数据可视化
Pandas高级教程:数据清洗、转换与分析
Pandas是Python的数据分析库,提供Series和DataFrame数据结构及数据分析工具,便于数据清洗、转换和分析。本教程涵盖Pandas在数据清洗(如缺失值、重复值和异常值处理)、转换(数据类型转换和重塑)和分析(如描述性统计、分组聚合和可视化)的应用。通过学习Pandas,用户能更高效地处理和理解数据,为数据分析任务打下基础。
1362 3
|
索引 Python
Pandas 2.2 中文官方教程和指南(一)(4)
Pandas 2.2 中文官方教程和指南(一)
144 0
|
存储 SQL JSON
Pandas 2.2 中文官方教程和指南(一)(3)
Pandas 2.2 中文官方教程和指南(一)
200 0
|
XML 关系型数据库 PostgreSQL
Pandas 2.2 中文官方教程和指南(一)(2)
Pandas 2.2 中文官方教程和指南(一)
389 0
|
XML 关系型数据库 MySQL
Pandas 2.2 中文官方教程和指南(一)(1)
Pandas 2.2 中文官方教程和指南(一)
551 0
|
C++ 索引 Python
Pandas 2.2 中文官方教程和指南(五)(4)
Pandas 2.2 中文官方教程和指南(五)
116 0