当前位置: 首页>>技术问答>>正文


python - dataframe的iloc,ix和loc有何不同?

技术问答 , , , , , , 去评论

DataFrame的iloc,ix和loc这三种切片方法有何不同吗?

之前看过一些官方文档,但还是无法理解这三者之间的区别。

例如,假设我们要获取DataFrame的前五行。这三者内部是如何实现的?求解释!

df.loc[:5]
df.ix[:5]
df.iloc[:5]

最佳回答

iloc基于整数定位。因此,无论您的行标签是什么,您始终可以例如通过执行以下操作获得第一行

df.iloc[0]

或最后五行

df.iloc[-5:]

您也可以在列上使用它。这将检索第三列:

df.iloc[:, 2]    # the : in the first position indicates all rows

您可以将它们结合起来以获得行和列的交集

df.iloc[:3, :3] # The upper-left 3 X 3 entries (assuming df has 3+ rows and columns)

另一方面,.loc使用命名索引。给定一个带有字符串作为行和列标签的DataFrame:

df = pd.DataFrame(index=['a', 'b', 'c'], columns=['time', 'date', 'name'])

然后我们可以得到第一行

df.loc['a']     # equivalent to df.iloc[0]

'date'列的后两行

df.loc['b':, 'date']   # equivalent to df.iloc[1:, 1]

可能值得指出的是,DataFrame的默认行和列索引是从0开始的整数。如果您有非数字索引,例如字符串或日期时间,则df.loc[:5]会引发错误。

另外,您可以使用DataFrame的__getitem__进行列检索:

df['time']    # equivalent to df.loc[:, 'time']

如果您要混合使用位置索引和命名索引,比如说使用行上的名称和列上的位置进行索引。这通常需要用.ix

df.ix[:2, 'time']    # the first two rows of the 'time' column

另外值得一提的是,您也可以将布尔向量传递给loc方法。例如:

 b = [True, False, True]
 df.loc[b] 

将返回df的第一行和第三行。这等效于df[b]进行选择,但也可以用于通过布尔向量进行内容设置:

df.loc[b, 'name'] = 'Mary', 'John'

 

次佳回答

 


.ix已弃用且含糊不清,切勿使用

由于不建议使用.ix,因此我们仅关注.loc.iloc之间的差异。

在讨论差异之前,重要的是要了解DataFrame的这个特点:具有用于帮助标识每个列和每个索引的标签。让我们看一个示例DataFrame:

df = pd.DataFrame({'age':[30, 2, 12, 4, 32, 33, 69],
                   'color':['blue', 'green', 'red', 'white', 'gray', 'black', 'red'],
                   'food':['Steak', 'Lamb', 'Mango', 'Apple', 'Cheese', 'Melon', 'Beans'],
                   'height':[165, 70, 120, 80, 180, 172, 150],
                   'score':[4.6, 8.3, 9.0, 3.3, 1.8, 9.5, 2.2],
                   'state':['NY', 'TX', 'FL', 'AL', 'AK', 'TX', 'TX']
                   },
                  index=['Jane', 'Nick', 'Aaron', 'Penelope', 'Dean', 'Christina', 'Cornelia'])

所有粗体字均为标签。列使用标签agecolorfoodheightscorestate列。索引使用的是标签JaneNickAaronPenelopeDeanChristinaCornelia


选择DataFrame中特定行的主要方法是使用.loc.iloc索引器。此外,每个索引器都使用紧跟其名称的一组方括号来进行选择。这些索引器也都可以用于选择列,这里为了简便起见,只探讨行的选择。

.loc仅通过标签选择数据

我们将首先讨论.loc索引器,该索引器仅通过索引或列标签选择数据。在示例DataFrame中,我们提供了有意义的名称作为索引值。许多DataFrame都没有任何有意义的名称,而是默认为0到n-1之间的整数,其中n是DataFrame的长度。

您可以为.loc使用三种不同的输入

  • 一个字符串
  • 字符串列表
  • 使用字符串作为起始值和终止值的切片符号

用带字符串的.loc选择单行

要选择单行数据,请将索引标签放在.loc之后的括号内。

df.loc['Penelope']

这将数据行作为Series(序列)返回

age           4
color     white
food      Apple
height       80
score       3.3
state        AL
Name: Penelope, dtype: object

使用.loc与多个字符串列表选择多行

df.loc[['Cornelia', 'Jane', 'Dean']]

这将返回一个DataFrame,其中的数据行按列表中指定的顺序排列:

使用带有切片符号的.loc选择多行

切片符号由“开始”,“停止”和“步长”三个值定义。按标签切片时, Pandas 在返回值中包含停止值。以下是从Aaron(亚伦)到Dean(迪恩(含))的片段。它的步长未明确定义,但默认为1。

df.loc['Aaron':'Dean']

可以采用与Python列表相同的方式获取复杂的切片。

.iloc仅按整数位置选择数据

DataFrame中数据的每一行和每一列都有一个定义它的整数位置。这是输出中直观显示的标签的补充。整数位置是以左上角为原点(0)开始的行或列的数量。

您可以为.iloc使用三种不同的输入

  • 一个整数
  • 整数列表
  • 使用整数作为起始值和终止值的切片符号

用带整数的.iloc选择单行

df.iloc[4]

这将返回第5行(整数位置4)Series(序列)

age           32
color       gray
food      Cheese
height       180
score        1.8
state         AK
Name: Dean, dtype: object

用.iloc选择带有整数列表的多行

df.iloc[[2, -2]]

这将返回第三行和倒数第二行的DataFrame:

使用带切片符号的.iloc选择多行

df.iloc[:5:3]  # 从第0行开始到第5行,步长为3


使用.loc和.iloc同时选择行和列

.loc和.iloc的一项出色功能是可以同时选择行和列。我们只需要用逗号分隔行和列选择即可。

例如,我们可以选择Jane行和Dean行,它们的高度,得分和状态列如下:

df.loc[['Jane', 'Dean'], 'height':]

上面的示例对行使用标签列表,对列使用切片符号

也可以只使用整数对.iloc进行类似的操作。

df.iloc[[1,4], 2]
Nick      Lamb
Dean    Cheese
Name: food, dtype: object

用标签和整数位置同时选择

.ix用于同时使用标签和整数位置进行选择,这虽然有用,但有时会造成混淆和歧义,但值得庆幸的是它已被弃用。如果您需要混合使用标签和整数位置进行选择,则必须同时选择标签或整数位置。

例如,如果我们要选择Nick行和Cornelia行以及第2列和第4列,则可以使用.loc,方法是将整数转换为带有以下内容的标签:

col_names = df.columns[[2, 4]]
df.loc[['Nick', 'Cornelia'], col_names] 

或者,可以使用get_loc索引方法将索引标签转换为整数。

labels = ['Nick', 'Cornelia']
index_ints = [df.index.get_loc(label) for label in labels]
df.iloc[index_ints, [2, 4]]

布尔选择

.loc索引器还可以进行布尔选择。例如,如果我们有兴趣查找年龄在30岁以上的所有行,并仅返回foodscore列,则可以执行以下操作:

df.loc[df['age'] > 30, ['food', 'score']] 

您可以使用.iloc实现类似的功能,但不能将其传递为布尔Series(系列),而必须将boolean Series转换为numpy数组,如下所示:

df.iloc[(df['age'] > 30).values, [2, 4]] 

选择所有行[即做列选择]

可以将.loc和.iloc用于仅列选择。您可以使用如下冒号来选择所有行:

df.loc[:, 'color':'score':2]


索引运算符[]也可以选择行和列,但不能同时选择。

大多数人都熟悉DataFrame索引运算符的主要目的,即选择列。字符串选择单个列作为系列,而字符串列表选择多个列作为DataFrame。

df['food']

Jane          Steak
Nick           Lamb
Aaron         Mango
Penelope      Apple
Dean         Cheese
Christina     Melon
Cornelia      Beans
Name: food, dtype: object

使用列表选择多个列

df[['food', 'score']]

人们所不熟悉的是,当使用切片符号时,选择是通过行标签或整数位置进行的。这非常令人困惑,我几乎从未使用过,但是确实可以使用。

df['Penelope':'Christina'] # slice rows by label

df[2:6:2] # slice rows by integer location,第3个数字是步长

注意:单独的索引运算符无法同时选择行和列。

df[3:5, 'color']
TypeError: unhashable type: 'slice'

参考资料

 

本文由《纯净天空》出品。文章地址: https://vimsky.com/article/4361.html,未经允许,请勿转载。