版本 0.21.0(2017 年 10 月 27 日)#

这是 0.20.3 的主要版本,包括大量 API 更改、弃用、新功能、增强功能和性能改进以及大量错误修复。我们建议所有用户升级到此版本。

亮点包括:

  • 与Apache Parquet集成,包括新的顶级read_parquet()函数和DataFrame.to_parquet()方法,请参见此处

  • pandas.api.types.CategoricalDtype用于指定独立于数据的分类的新面向用户,请参阅此处

  • sum所有 NaN 系列/数据帧上的和的行为prod现在是一致的,不再取决于是否安装了瓶颈sum,并且prod空系列上的 和 现在返回 NaN 而不是 0,请参见此处

  • pypy 的兼容性修复,请参阅此处

  • dropreindexrenameAPI 进行了补充,使它们更加一致,请参阅此处

  • 添加新方法DataFrame.infer_objects(请参见此处)和GroupBy.pipe(请参见此处)。

  • 使用标签列表进行索引(其中缺少一个或多个标签)已被弃用,并且会在未来版本中引发 KeyError,请参阅此处

更新前请检查API 更改弃用。

新功能

与 Apache Parquet 文件格式集成#

与Apache Parquet集成,包括新的顶层read_parquet()DataFrame.to_parquet()方法,请参见此处GH 15838GH 17438)。

Apache Parquet提供了一种跨语言的二进制文件格式,用于高效地读写数据帧。 Parquet 旨在忠实地序列化和反序列化DataFrame,支持所有 pandas 数据类型,包括扩展数据类型,例如带时区的日期时间。

此功能取决于pyarrowfastparquet库。有关更多详细信息,请参阅Parquet 上的 IO 文档

方法infer_objects类型转换#

添加了DataFrame.infer_objects()Series.infer_objects() 方法来对对象列执行数据类型推断,替换了已弃用方法的一些功能convert_objects 。请参阅此处的文档 了解更多详细信息。 (GH 11221

此方法仅对对象列执行软转换,将 Python 对象转换为本机类型,但不执行任何强制转换。例如:

In [1]: df = pd.DataFrame({'A': [1, 2, 3],
   ...:                    'B': np.array([1, 2, 3], dtype='object'),
   ...:                    'C': ['1', '2', '3']})
   ...: 

In [2]: df.dtypes
Out[2]: 
A     int64
B    object
C    object
Length: 3, dtype: object

In [3]: df.infer_objects().dtypes
Out[3]: 
A     int64
B     int64
C    object
Length: 3, dtype: object

请注意,列'C'未转换 - 只有标量数字类型将转换为新类型。其他类型的转换应使用to_numeric()函数(或to_datetime(), )来完成to_timedelta()

In [4]: df = df.infer_objects()

In [5]: df['C'] = pd.to_numeric(df['C'], errors='coerce')

In [6]: df.dtypes
Out[6]: 
A    int64
B    int64
C    int64
Length: 3, dtype: object

改进了尝试创建列时的警告#

新用户经常对实例上的列操作和属性访问之间的关系感到困惑DataFrameGH 7175)。这种混淆的一个具体实例是尝试通过在以下位置设置属性来创建新列DataFrame

In [1]: df = pd.DataFrame({'one': [1., 2., 3.]})
In [2]: df.two = [4, 5, 6]

这不会引发任何明显的异常,但也不会创建新列:

In [3]: df
Out[3]:
    one
0  1.0
1  2.0
2  3.0

现在,将类似列表的数据结构设置为新属性会引发UserWarning意外行为的可能性。请参阅属性访问

方法drop现在还接受索引/列关键字#

drop()方法已获得index/columns关键字作为指定axis.这类似于reindexGH 12392)的行为。

例如:

In [7]: df = pd.DataFrame(np.arange(8).reshape(2, 4),
   ...:                   columns=['A', 'B', 'C', 'D'])
   ...: 

In [8]: df
Out[8]: 
   A  B  C  D
0  0  1  2  3
1  4  5  6  7

[2 rows x 4 columns]

In [9]: df.drop(['B', 'C'], axis=1)
Out[9]: 
   A  D
0  0  3
1  4  7

[2 rows x 2 columns]

# the following is now equivalent
In [10]: df.drop(columns=['B', 'C'])
Out[10]: 
   A  D
0  0  3
1  4  7

[2 rows x 2 columns]

方法renamereindex现在也接受 axis 关键字#

DataFrame.rename()和方法DataFrame.reindex()已获得axis关键字来指定操作的目标轴(GH 12392)。

这是rename

In [11]: df = pd.DataFrame({"A": [1, 2, 3], "B": [4, 5, 6]})

In [12]: df.rename(str.lower, axis='columns')
Out[12]: 
   a  b
0  1  4
1  2  5
2  3  6

[3 rows x 2 columns]

In [13]: df.rename(id, axis='index')
Out[13]: 
                 A  B
140682504175824  1  4
140682504175856  2  5
140682504175888  3  6

[3 rows x 2 columns]

reindex

In [14]: df.reindex(['A', 'B', 'C'], axis='columns')
Out[14]: 
   A  B   C
0  1  4 NaN
1  2  5 NaN
2  3  6 NaN

[3 rows x 3 columns]

In [15]: df.reindex([0, 1, 3], axis='index')
Out[15]: 
     A    B
0  1.0  4.0
1  2.0  5.0
3  NaN  NaN

[3 rows x 2 columns]

“索引、列”样式继续像以前一样工作。

In [16]: df.rename(index=id, columns=str.lower)
Out[16]: 
                 a  b
140682504175824  1  4
140682504175856  2  5
140682504175888  3  6

[3 rows x 2 columns]

In [17]: df.reindex(index=[0, 1, 3], columns=['A', 'B', 'C'])
Out[17]: 
     A    B   C
0  1.0  4.0 NaN
1  2.0  5.0 NaN
3  NaN  NaN NaN

[3 rows x 3 columns]

我们强烈鼓励使用命名参数,以避免在使用任何一种风格时出现混淆。

CategoricalDtype用于指定分类#

pandas.api.types.CategoricalDtype已添加到公共 API 并扩展为包含categoriesordered属性。 A CategoricalDtype可用于指定类别集和数组的有序性,与数据无关。例如,当将字符串数据转换为CategoricalGH 14711GH 15078GH 16015GH 17643)时,这可能很有用:

In [18]: from pandas.api.types import CategoricalDtype

In [19]: s = pd.Series(['a', 'b', 'c', 'a'])  # strings

In [20]: dtype = CategoricalDtype(categories=['a', 'b', 'c', 'd'], ordered=True)

In [21]: s.astype(dtype)
Out[21]: 
0    a
1    b
2    c
3    a
Length: 4, dtype: category
Categories (4, object): ['a' < 'b' < 'c' < 'd']

值得特别一提的一个地方是在read_csv()。以前,使用 时 ,返回的值和类别始终是字符串。dtype={'col': 'category'}

In [22]: data = 'A,B\na,1\nb,2\nc,3'

In [23]: pd.read_csv(StringIO(data), dtype={'B': 'category'}).B.cat.categories
Out[23]: Index(['1', '2', '3'], dtype='object')

注意“对象”数据类型。

通过CategoricalDtype所有数字、日期时间或时间增量,我们可以自动转换为正确的类型

In [24]: dtype = {'B': CategoricalDtype([1, 2, 3])}

In [25]: pd.read_csv(StringIO(data), dtype=dtype).B.cat.categories
Out[25]: Index([1, 2, 3], dtype='int64')

这些值已被正确解释为整数。

.dtypea 或具有分类类型的 a 的属性Categorical现在CategoricalIndex将 返回Series的实例 CategoricalDtype。虽然 repr 发生了变化,但str(CategoricalDtype())string 仍然是'category'。我们将借此机会提醒用户, 检测分类数据的首选方法是使用 pandas.api.types.is_categorical_dtype(), 而不是。str(dtype) == 'category'

有关更多信息,请参阅CategoricalDtype 文档

GroupBy对象现在有一个pipe方法#

GroupBy对象现在有一个pipe方法,类似于 DataFrame和上的方法Series,它允许 GroupBy以干净、可读的语法组成接受 a 的函数。 (GH 17871

.groupby对于组合和 的具体示例.pipe,想象一下有一个包含商店、产品、收入和销售数量列的 DataFrame。我们希望对每个商店和每个产品的价格(即收入/数量)进行分组计算。我们可以通过多步操作来完成此操作,但用管道表示可以使代码更具可读性。

首先我们设置数据:

In [26]: import numpy as np

In [27]: n = 1000

In [28]: df = pd.DataFrame({'Store': np.random.choice(['Store_1', 'Store_2'], n),
   ....:                    'Product': np.random.choice(['Product_1',
   ....:                                                 'Product_2',
   ....:                                                 'Product_3'
   ....:                                                 ], n),
   ....:                    'Revenue': (np.random.random(n) * 50 + 10).round(2),
   ....:                    'Quantity': np.random.randint(1, 10, size=n)})
   ....: 

In [29]: df.head(2)
Out[29]: 
     Store    Product  Revenue  Quantity
0  Store_2  Product_2    32.09         7
1  Store_1  Product_3    14.20         1

[2 rows x 4 columns]

现在,要查找每个商店/产品的价格,我们可以简单地执行以下操作:

In [30]: (df.groupby(['Store', 'Product'])
   ....:    .pipe(lambda grp: grp.Revenue.sum() / grp.Quantity.sum())
   ....:    .unstack().round(2))
   ....: 
Out[30]: 
Product  Product_1  Product_2  Product_3
Store                                   
Store_1       6.73       6.72       7.14
Store_2       7.59       6.98       7.23

[2 rows x 3 columns]

请参阅文档了解更多信息。

Categorical.rename_categories接受类似字典的#

rename_categories()现在接受类似字典的参数 new_categories。在字典的键中查找先前的类别,如果找到则替换。丢失和多余键的行为与 中的相同DataFrame.rename()

In [31]: c = pd.Categorical(['a', 'a', 'b'])

In [32]: c.rename_categories({"a": "eh", "b": "bee"})
Out[32]: 
['eh', 'eh', 'bee']
Categories (2, object): ['eh', 'bee']

警告

为了帮助升级 pandas,rename_categories将其视为Series类似列表。通常,Series 被认为是类似字典的(例如,在 .rename,中.map)。在 Pandas 的未来版本中,rename_categories 它们将被视为类似字典。请遵循警告消息的建议来编写面向未来的代码。

In [33]: c.rename_categories(pd.Series([0, 1], index=['a', 'c']))
FutureWarning: Treating Series 'new_categories' as a list-like and using the values.
In a future version, 'rename_categories' will treat Series like a dictionary.
For dict-like, use 'new_categories.to_dict()'
For list-like, use 'new_categories.values'.
Out[33]:
[0, 0, 1]
Categories (2, int64): [0, 1]

其他增强功能#

新函数或方法#

新关键词#

各种增强功能#

向后不兼容的 API 更改#

依赖项增加了最低版本#

我们更新了依赖项的最低支持版本(GH 15206GH 15543GH 15214)。如果安装了,我们现在需要:

包裹

最低版本

必需的

麻木

1.9.0

X

Matplotlib

1.4.3

西皮

0.14.0

瓶颈

1.0.0

此外,已放弃对 Python 3.4 ( GH 15251 ) 的支持。

全 NaN 或空 Series/DataFrame 的和/积现在始终为 NaN #

笔记

此处描述的更改已部分恢复。有关更多信息,请参阅v0.22.0 Whatsnew

sum全 NaN Series/DataFrame 的和的行为prod不再取决于是否安装了瓶颈,并且空系列的sum和 的返回值已更改( GH 9422GH 15507)。prod

对a 的空或全或列调用sumor将得到。请参阅文档prodNaN SeriesDataFrameNaN

In [33]: s = pd.Series([np.nan])

以前没有bottleneck安装:

In [2]: s.sum()
Out[2]: np.nan

以前与bottleneck

In [2]: s.sum()
Out[2]: 0.0

新行为,不考虑瓶颈安装:

In [34]: s.sum()
Out[34]: 0.0

请注意,这也会更改空的总和Series。以前,无论bottleneck安装如何,它总是返回 0:

In [1]: pd.Series([]).sum()
Out[1]: 0

但为了与全 NaN 情况保持一致,这也更改为返回 0:

In [2]: pd.Series([]).sum()
Out[2]: 0

不推荐使用缺少标签的列表进行索引#

以前,使用标签列表进行选择时,如果缺少一个或多个标签,则始终会成功,并返回NaN缺少的标签。现在将显示一个FutureWarning.将来这将提出一个KeyErrorGH 15747)。当使用或传递至少有 1 个缺失标签的标签列表时,将触发此警告DataFrameSeries.loc[][[]]

In [35]: s = pd.Series([1, 2, 3])

In [36]: s
Out[36]: 
0    1
1    2
2    3
Length: 3, dtype: int64

以前的行为

In [4]: s.loc[[1, 2, 3]]
Out[4]:
1    2.0
2    3.0
3    NaN
dtype: float64

目前的行为

In [4]: s.loc[[1, 2, 3]]
Passing list-likes to .loc or [] with any missing label will raise
KeyError in the future, you can use .reindex() as an alternative.

See the documentation here:
https://pandas.pydata.org/pandas-docs/stable/indexing.html#deprecate-loc-reindex-listlike

Out[4]:
1    2.0
2    3.0
3    NaN
dtype: float64

实现选择可能未找到的元素的惯用方法是通过.reindex()

In [37]: s.reindex([1, 2, 3])
Out[37]: 
1    2.0
2    3.0
3    NaN
Length: 3, dtype: float64

找到的所有键的选择保持不变。

In [38]: s.loc[[1, 2]]
Out[38]: 
1    2
2    3
Length: 2, dtype: int64

不适用命名更改#

为了提高 pandas API 之间的一致性,我们添加了额外的顶级函数isna()和的notna()别名。命名方案现在与和等方法更加一致。此外,在定义和方法的所有情况下,这些方法都有名为和 的附加方法,这些方法包含在类、 、和 中。 (GH 15001)。isnull()notnull().dropna().fillna().isnull().notnull().isna().notna()CategoricalIndexSeriesDataFrame

该配置选项pd.options.mode.use_inf_as_null已弃用,并pd.options.mode.use_inf_as_na作为替代选项添加。

系列/索引的迭代现在将返回 Python 标量#

Series以前,当对dtypeint或 的a 使用某些迭代方法时float,您将收到一个numpy标量,例如 a np.int64,而不是 Python int。问题 ( GH 10904 ) 更正了Series.tolist()和 的问题list(Series)。此更改使所有迭代方法保持一致,特别是 for__iter__().map();请注意,这仅影响 int/float 数据类型。 (GH 13236GH 13258GH 14216)。

In [39]: s = pd.Series([1, 2, 3])

In [40]: s
Out[40]: 
0    1
1    2
2    3
Length: 3, dtype: int64

之前:

In [2]: type(list(s)[0])
Out[2]: numpy.int64

新行为:

In [41]: type(list(s)[0])
Out[41]: int

DataFrame.to_dict()此外,这现在也可以正确地对迭代结果进行装箱。

In [42]: d = {'a': [1], 'b': ['b']}

In [43]: df = pd.DataFrame(d)

之前:

In [8]: type(df.to_dict()['a'][0])
Out[8]: numpy.int64

新行为:

In [44]: type(df.to_dict()['a'][0])
Out[44]: int

使用布尔索引进行索引#

以前,当将布尔值传递Index给 时.loc,如果 的索引Series/DataFrameboolean标签,您将获得基于标签的选择,可能会重复结果标签,而不是布尔索引选择(其中True选择元素),这与布尔 numpy 数组的索引方式不一致。新行为就像布尔 numpy 数组索引器一样。 (GH 17738

以前的行为:

In [45]: s = pd.Series([1, 2, 3], index=[False, True, False])

In [46]: s
Out[46]: 
False    1
True     2
False    3
Length: 3, dtype: int64
In [59]: s.loc[pd.Index([True, False, True])]
Out[59]:
True     2
False    1
False    3
True     2
dtype: int64

目前的行为

In [47]: s.loc[pd.Index([True, False, True])]
Out[47]: 
False    1
False    3
Length: 2, dtype: int64

此外,以前如果您有一个非数字索引(例如字符串),那么布尔索引将引发KeyError.现在,这将被视为布尔索引器。

以前的行为:

In [48]: s = pd.Series([1, 2, 3], index=['a', 'b', 'c'])

In [49]: s
Out[49]: 
a    1
b    2
c    3
Length: 3, dtype: int64
In [39]: s.loc[pd.Index([True, False, True])]
KeyError: "None of [Index([True, False, True], dtype='object')] are in the [index]"

目前的行为

In [50]: s.loc[pd.Index([True, False, True])]
Out[50]: 
a    1
c    3
Length: 2, dtype: int64

PeriodIndex重新采样#

在 pandas 的早期版本中,在某些情况下,对由返回的 a索引的 a Series/重新采样( GH 12884)。重新采样到倍频现在会返回( GH 15944 )。作为一个小的增强,重新采样现在可以处理值(GH 13224DataFramePeriodIndexDatetimeIndexPeriodIndexPeriodIndexNaT

以前的行为:

In [1]: pi = pd.period_range('2017-01', periods=12, freq='M')

In [2]: s = pd.Series(np.arange(12), index=pi)

In [3]: resampled = s.resample('2Q').mean()

In [4]: resampled
Out[4]:
2017-03-31     1.0
2017-09-30     5.5
2018-03-31    10.0
Freq: 2Q-DEC, dtype: float64

In [5]: resampled.index
Out[5]: DatetimeIndex(['2017-03-31', '2017-09-30', '2018-03-31'], dtype='datetime64[ns]', freq='2Q-DEC')

新行为:

In [1]: pi = pd.period_range('2017-01', periods=12, freq='M')

In [2]: s = pd.Series(np.arange(12), index=pi)

In [3]: resampled = s.resample('2Q').mean()

In [4]: resampled
Out[4]:
2017Q1    2.5
2017Q3    8.5
Freq: 2Q-DEC, dtype: float64

In [5]: resampled.index
Out[5]: PeriodIndex(['2017Q1', '2017Q3'], dtype='period[2Q-DEC]')

上采样和调用.ohlc()之前返回 a Series,与调用基本相同.asfreq()。 OHLC 上采样现在返回包含列openhigh和( GH 13083low )的DataFrame 。这与下采样和行为一致。closeDatetimeIndex

以前的行为:

In [1]: pi = pd.period_range(start='2000-01-01', freq='D', periods=10)

In [2]: s = pd.Series(np.arange(10), index=pi)

In [3]: s.resample('H').ohlc()
Out[3]:
2000-01-01 00:00    0.0
                ...
2000-01-10 23:00    NaN
Freq: H, Length: 240, dtype: float64

In [4]: s.resample('M').ohlc()
Out[4]:
         open  high  low  close
2000-01     0     9    0      9

新行为:

In [56]: pi = pd.period_range(start='2000-01-01', freq='D', periods=10)

In [57]: s = pd.Series(np.arange(10), index=pi)

In [58]: s.resample('H').ohlc()
Out[58]:
                  open  high  low  close
2000-01-01 00:00   0.0   0.0  0.0    0.0
2000-01-01 01:00   NaN   NaN  NaN    NaN
2000-01-01 02:00   NaN   NaN  NaN    NaN
2000-01-01 03:00   NaN   NaN  NaN    NaN
2000-01-01 04:00   NaN   NaN  NaN    NaN
...                ...   ...  ...    ...
2000-01-10 19:00   NaN   NaN  NaN    NaN
2000-01-10 20:00   NaN   NaN  NaN    NaN
2000-01-10 21:00   NaN   NaN  NaN    NaN
2000-01-10 22:00   NaN   NaN  NaN    NaN
2000-01-10 23:00   NaN   NaN  NaN    NaN

[240 rows x 4 columns]

In [59]: s.resample('M').ohlc()
Out[59]:
         open  high  low  close
2000-01     0     9    0      9

[1 rows x 4 columns]

改进了 pd.eval 中项目分配期间的错误处理#

eval()ValueError现在,当项目分配出现故障或指定了就地操作,但表达式中没有项目分配时,将引发 a ( GH 16732 )

In [51]: arr = np.array([1, 2, 3])

以前,如果您尝试使用以下表达式,您会收到一条不太有用的错误消息:

In [3]: pd.eval("a = 1 + 2", target=arr, inplace=True)
...
IndexError: only integers, slices (`:`), ellipsis (`...`), numpy.newaxis (`None`)
and integer or boolean arrays are valid indices

这是一个很长的说法,说明 numpy 数组不支持字符串项索引。经过此更改,错误消息现在是这样的:

In [3]: pd.eval("a = 1 + 2", target=arr, inplace=True)
...
ValueError: Cannot assign expression output to target

即使没有项目分配,过go也可以就地计算表达式:

In [4]: pd.eval("1 + 2", target=arr, inplace=True)
Out[4]: 3

然而,这个输入没有多大意义,因为输出没有分配给目标。现在,ValueError当传入这样的输入时,将引发 a :

In [4]: pd.eval("1 + 2", target=arr, inplace=True)
...
ValueError: Cannot operate inplace if there is no assignment

数据类型转换#

以前的赋值.where().fillna()赋值bool会强制转换为相同的类型(例如 int / float),或者为 datetimelikes 引发。这些现在将保留具有 dtypes 的布尔值object。 (GH 16821)。

In [52]: s = pd.Series([1, 2, 3])
In [5]: s[1] = True

In [6]: s
Out[6]:
0    1
1    1
2    3
dtype: int64

新行为

In [7]: s[1] = True

In [8]: s
Out[8]:
0       1
1    True
2       3
Length: 3, dtype: object

以前,将非日期时间类分配给日期时间类会强制分配非日期时间类项目(GH 14145)。

In [53]: s = pd.Series([pd.Timestamp('2011-01-01'), pd.Timestamp('2012-01-01')])
In [1]: s[1] = 1

In [2]: s
Out[2]:
0   2011-01-01 00:00:00.000000000
1   1970-01-01 00:00:00.000000001
dtype: datetime64[ns]

这些现在强制为objectdtype。

In [1]: s[1] = 1

In [2]: s
Out[2]:
0    2011-01-01 00:00:00
1                      1
dtype: object
  • 与 datetimelikes 的行为不一致.where(),这会引发而不是强制objectGH 16402

  • 对带有dtype 的int64数据进行赋值时出现的错误可能会保留dtype ( GH 14001 )np.ndarrayfloat64int64

具有单级的 MultiIndex 构造函数#

构造MultiIndex函数不再将所有长度为 1 级别的 MultiIndex 压缩为常规Index.这会影响所有 MultiIndex构造函数。 (GH 17178

以前的行为:

In [2]: pd.MultiIndex.from_tuples([('a',), ('b',)])
Out[2]: Index(['a', 'b'], dtype='object')

长度 1 级别不再有特殊情况。它们的行为与长度为 2+ 的级别完全相同,因此 aMultiIndex始终从所有 MultiIndex构造函数返回:

In [54]: pd.MultiIndex.from_tuples([('a',), ('b',)])
Out[54]: 
MultiIndex([('a',),
            ('b',)],
           )

UTC 本地化系列#

以前,传递时to_datetime()不会本地化日期时间Series数据。utc=True现在,将使用数据类型to_datetime()正确本地化,以与列表和数据的处理方式保持一致。 (GH 6415)。Seriesdatetime64[ns, UTC]Index

以前的行为

In [55]: s = pd.Series(['20130101 00:00:00'] * 3)
In [12]: pd.to_datetime(s, utc=True)
Out[12]:
0   2013-01-01
1   2013-01-01
2   2013-01-01
dtype: datetime64[ns]

新行为

In [56]: pd.to_datetime(s, utc=True)
Out[56]: 
0   2013-01-01 00:00:00+00:00
1   2013-01-01 00:00:00+00:00
2   2013-01-01 00:00:00+00:00
Length: 3, dtype: datetime64[ns, UTC]

此外,仅当原始 SQL 列是时区感知的日期时间列时,包含由日期时间列解析的 DataFrameread_sql_table()才会本地化为 UTC。read_sql_query()

范围函数的一致性#

在以前的版本中,各种范围函数之间存在一些不一致:date_range()bdate_range()period_range()timedelta_range()interval_range()。 (GH 17471)。

start当、endperiod参数全部指定时,会出现不一致的行为之一,这可能会导致范围不明确。当所有三个参数都被传递时,interval_range忽略该period参数,period_range忽略该end参数,并引发其他范围函数。为了促进范围函数之间的一致性,并避免潜在的不明确范围,interval_range现在period_range将在传递所有三个参数时引发。

以前的行为:

 In [2]: pd.interval_range(start=0, end=4, periods=6)
 Out[2]:
 IntervalIndex([(0, 1], (1, 2], (2, 3]]
               closed='right',
               dtype='interval[int64]')

In [3]: pd.period_range(start='2017Q1', end='2017Q4', periods=6, freq='Q')
Out[3]: PeriodIndex(['2017Q1', '2017Q2', '2017Q3', '2017Q4', '2018Q1', '2018Q2'], dtype='period[Q-DEC]', freq='Q-DEC')

新行为:

In [2]: pd.interval_range(start=0, end=4, periods=6)
---------------------------------------------------------------------------
ValueError: Of the three parameters: start, end, and periods, exactly two must be specified

In [3]: pd.period_range(start='2017Q1', end='2017Q4', periods=6, freq='Q')
---------------------------------------------------------------------------
ValueError: Of the three parameters: start, end, and periods, exactly two must be specified

此外,端点参数end不包含在 生成的间隔中interval_range。但是,所有其他范围函数都包含end在其输出中。为了促进范围函数之间的一致性,interval_range现在将包括end作为最终间隔的右端点,除非freq以跳过 的方式指定if end

以前的行为:

In [4]: pd.interval_range(start=0, end=4)
Out[4]:
IntervalIndex([(0, 1], (1, 2], (2, 3]]
              closed='right',
              dtype='interval[int64]')

新行为:

In [57]: pd.interval_range(start=0, end=4)
Out[57]: IntervalIndex([(0, 1], (1, 2], (2, 3], (3, 4]], dtype='interval[int64, right]')

没有自动 Matplotlib 转换器#

导入 pandas 时,pandas 不再向 matplotlib 注册我们的datetimedatetimedatetime64和转换器。 PeriodMatplotlib 绘图方法(plt.plotax.plot、...)无法很好地格式化 x 轴DatetimeIndexPeriodIndex值。您必须显式注册这些方法:

pandas 内置,Series.plot并将在首次使用时注册这些转换器(DataFrame.plot GH 17710)。

笔记

此更改已在 pandas 0.21.1 中暂时恢复,有关更多详细信息,请参见此处

其他 API 更改#

  • 分类构造函数不再接受关键字标量categories。 (GH 16022

  • 访问关闭上不存在的属性HDFStore现在将引发一个AttributeError而不是一个ClosedFileErrorGH 16301

  • read_csv()UserWarning如果names参数包含重复项,现在会发出 a ( GH 17095 )

  • read_csv()现在默认将'null''n/a'字符串视为缺失值(GH 16471GH 16078

  • pandas.HDFStore的字符串表示现在更快且更不详细。对于之前的行为,请使用pandas.HDFStore.info(). (GH 16503)。

  • HDF 存储中的压缩默认值现在遵循 pytables 标准。默认为不压缩,如果complib缺少且使用complevel> 0 ( GH 15943 )zlib

  • Index.get_indexer_non_unique()现在返回一个 ndarray 索引器而不是Index;这与Index.get_indexer()GH 16819)一致

  • @slow从 中删除了装饰器pandas._testing,这导致一些下游包的测试套件出现问题。使用@pytest.mark.slow代替,可以实现相同的效果(GH 16850

  • 将 的定义移至MergeError模块pandas.errors

  • Series.set_axis()和的签名DataFrame.set_axis()已从 更改为,以便与 API 的其余部分保持一致。旧签名已弃用,并将显示( GH 14636 )set_axis(axis, labels)set_axis(labels, axis=0)FutureWarning

  • Series.argmin()现在与 dtypes 一起使用时Series.argmax()将引发 a ,而不是( GH 13595 )TypeErrorobjectValueError

  • PeriodAttributeError现在是不可变的,并且当用户尝试为ordinal或属性分配新值时将引发 an freq( GH 17116 )。

  • to_datetime()当通过时,具有 tz 意识的origin=kwarg 现在将提出更具信息性的信息,ValueError而不是TypeErrorGH 16842

  • to_datetime()现在提出一个ValueError时间格式,包括%W%U不包括星期几和日历年(GH 16774

  • 将非功能性重命名indexindex_colinread_stata()以提高 API 一致性(GH 16342

  • 当从数字索引中删除索引时,错误DataFrame.drop()会导致布尔标签FalseTrue分别被视为标签 0 和 1。现在这将引发 ValueError ( GH 16877 )

  • 受限制的 DateOffset 关键字参数。以前,DateOffset子类允许任意关键字参数,这可能会导致意外行为。现在,只接受有效的论据。 (GH 17176)。

弃用#

Series.select 和 DataFrame.select #

不推荐使用Series.select()和方法,而改用( GH 12401 )DataFrame.select()df.loc[labels.map(crit)]

In [58]: df = pd.DataFrame({'A': [1, 2, 3]}, index=['foo', 'bar', 'baz'])
In [3]: df.select(lambda x: x in ['bar', 'baz'])
FutureWarning: select is deprecated and will be removed in a future release. You can use .loc[crit] as a replacement
Out[3]:
     A
bar  2
baz  3
In [59]: df.loc[df.index.map(lambda x: x in ['bar', 'baz'])]
Out[59]: 
     A
bar  2
baz  3

[2 rows x 1 columns]

Series.argmax 和 Series.argmin #

Series.argmax()和的行为Series.argmin()已分别被弃用,取而代之的是Series.idxmax()Series.idxmin()( GH 16830 )。

为了与 NumPy 数组兼容,pd.Series实现argmaxargmin.自 pandas 0.13.0 起,argmax一直是 的别名 pandas.Series.idxmax(),并且argmin一直是 的别名 pandas.Series.idxmin()。它们返回最大值或最小值的标签,而不是位置

Series.argmax我们已弃用和 的当前行为Series.argmin。使用其中任何一个都会发出一个FutureWarning.Series.idxmax()如果您想要最大值的标签,请使用 。Series.values.argmax()如果您想要最大值的位置,请使用 。对于最小值也是如此。在未来的版本中将Series.argmax返回Series.argmin最大值或最小值的位置。

删除先前版本的弃用/更改#

  • read_excel()已删除has_index_names参数(GH 10967

  • 配置pd.options.display.height已被删除(GH 3663

  • 配置pd.options.display.line_width已被删除(GH 2881

  • 配置pd.options.display.mpl_style已被删除(GH 12190

  • Index已放弃该.sym_diff()方法,转而采用.symmetric_difference()GH 12591

  • Categorical已放弃.order().sort()方法,转而采用.sort_values()( GH 12882 )

  • eval()并将DataFrame.eval()默认值inplace从更改NoneFalse( GH 11149 )

  • 该函数get_offset_name已被删除,取而代之的是.freqstr偏移量属性(GH 11834

  • pandas 不再测试与使用 pandas < 0.11 ( GH 17404 ) 创建的 hdf5 文件的兼容性。

性能改进#

文档更改#

Bug修复

转换

  • 针对类似日期时间的数据的赋值错误int可能会错误地转换为类似日期时间的数据(GH 14145

  • 对带有dtype 的int64数据进行赋值时出现的错误可能会保留dtype ( GH 14001 )np.ndarrayfloat64int64

  • 将 的返回类型修复IntervalIndex.is_non_overlapping_monotonic为 Python,bool以与类似属性/方法保持一致。之前返回了一个numpy.bool_. (GH 17237

  • IntervalIndex.is_non_overlapping_monotonic当间隔在两侧闭合并在一点重叠时出现错误( GH 16560

  • 当和是 dictSeries.fillna()时返回帧中的错误(GH 16156inplace=Truevalue

  • Timestamp.weekday_name本地化到时区时返回基于 UTC 的工作日名称时出现错误( GH 17354 )

  • 替换DST 更改Timestamp.replace时出现的错误( GH 15683 )tzinfo

  • 构造和算术中的错误Timedelta不会传播Overflow异常(GH 17367

  • astype()当传递扩展类型类(DatetimeTZDtypeCategoricalDtype)而不是实例时,转换为对象数据类型时出现错误。现在,TypeError当一个类通过时,会引发 a ( GH 17780 )。

  • 当(GH 17007GH 17125to_numeric()时,元素并不总是被强制为数字的错误errors='coerce'

  • 在 Windows 上将对象转换为dtype 而不是( GH 16804 )的错误DataFrameSeries构造函数rangeint32int64

索引#

  • 当使用空切片(例如df.iloc[:])调用时,.iloc.loc索引器返回原始对象的浅表副本。之前他们返回了原始对象。 (GH 13873)。

  • 当调用 unsorted 时MultiIndex,索引器现在只有在非排序级别使用正确的切片时loc才会引发( GH 16734)。UnsortedIndexError

  • TimedeltaIndex修复了 0.20.3 中使用 a ( GH 16896 )上的字符串进行索引时的回归。

  • 修复了输入TimedeltaIndex.get_loc()处理np.timedelta64GH 16909)。

  • 当参数是列表但未指定所有级别或采用不同顺序时修复MultiIndex.sort_index()排序( GH 16934)。ascending

  • np.inf修复了索引导致引发的错误OverflowErrorGH 16957

  • 在空的情况下重新索引时出现错误CategoricalIndexGH 16770

  • 修复了DataFrame.loc对齐和 tz 感知的设置DatetimeIndexGH 16889

  • IndexError使用较旧的 numpy传递索引或系列时避免.ilocGH 17193

  • 允许 unicode 空字符串作为 Python 2 中多级列中的占位符(GH 17099

  • .iloc与就地加法或赋值以及 int 索引器一起使用时出现的错误MultiIndex,导致读取和写入错误的索引(GH 17148

  • .isin()检查空对象中的成员资格Series引发错误的错误( GH 16991

  • 重新索引时出现错误CategoricalIndex,其中包含重复项的指定索引未得到尊重(GH 17323

  • RangeIndex与负步交集的错误( GH 17296

  • IntervalIndex对于包含的非重叠单调递减索引的右端点执行标量查找失败的错误( GH 16417GH 17271

  • 当没有有效条目时DataFrame.first_valid_index()出现错误( GH 17400DataFrame.last_valid_index()

  • 当使用可调用函数调用时Series.rename(),错误会错误地更改 的名称Series,而不是 的名称Index。 (GH 17407

  • 使用负索引时,引发错误String.str_get()而不是插入 NaN。 IndexErrorGH 17704

IO #

  • read_hdf()从 HDFStore 格式读取时区感知索引时出现错误fixedGH 17618

  • read_csv()未彻底删除列重复数据的错误( GH 17060 )

  • read_csv()未彻底消除指定列名称重复的错误( GH 17095 )

  • read_csv()标头参数的非整数值生成无用/不相关的错误消息的错误( GH 16338

  • read_csv()异常处理中的内存管理问题在某些情况下会导致解释器出现段错误( GH 14696GH 16798)。

  • read_csv()调用时出现错误low_memory=False,其中至少一列大小 > 2GB 的 CSV 会错误地引发MemoryError( GH 16798 )。

  • read_csv()使用单元素列表调用时出现的错误header将返回DataFrame所有 NaN 值 ( GH 7757 )

  • DataFrame.to_csv()Python 3 中默认使用“ascii”编码而不是“utf-8”的错误( GH 17097

  • read_stata()使用迭代器时无法读取值标签的错误( GH 16923

  • read_stata()未设置索引的错误( GH 16342

  • read_html()在多线程中运行时导入检查失败的错误( GH 16928 )

  • 当遇到坏行而不是正确的错误消息时,read_csv()自动分隔符检测导致抛出 a 的错误( GH 13374TypeError

  • 错误在于DataFrame.to_html()notebook=True具有命名索引或非 MultiIndex 索引的 DataFrame 分别对列或行标签进行了不需要的水平或垂直对齐(GH 16792

  • DataFrame.to_html()没有验证参数的错误justifyGH 17527

  • HDFStore.select()读取具有 VLArray 的连续混合数据表时出现错误( GH 17021

  • to_json()多个条件(包括具有不可打印符号的对象、具有深度递归的对象、过长标签的对象)导致段错误而不是引发适当的异常的错误( GH 14256

绘图#

  • secondary_y使用而不fontsize设置辅助轴字体大小的绘图方法中的错误( GH 12565

  • 在 y 轴上绘图timedelta和数据类型时出现错误( GH 16953datetime

  • 线图在计算 xlim 时不再假定单调 x 数据,即使对于未排序的 x 数据,它们现在也会显示整条线。 (GH 11310GH 11471

  • 对于 matplotlib 2.0.0 及更高版本,线图 x 限制的计算留给 matplotlib,以便应用其新的默认设置。 (GH 15495

  • 错误Series.plot.barDataFrame.plot.bary尊重用户传递colorGH 16822

  • plotting.parallel_coordinates使用随机颜色时导致重置随机种子的错误( GH 17525

GroupBy/重新采样/滚动#

  • DataFrame.resample(...).size()空的错误DataFrame没有返回Series( GH 14962 )

  • 导致infer_freq()工作周内有 2 天差距的指数被错误地推断为商业日报的错误(GH 16624

  • 错误地.rolling(...).quantile()使用了与Series.quantile()和不同的默认值DataFrame.quantile()GH 9413GH 16211

  • 错误groupby.transform()会强制布尔数据类型返回浮动(GH 16875

  • Series.resample(...).apply()Series修改源索引且未返回 a 的名称的错误Series( GH 14313 )

  • Bug in .rolling(...).apply(...)with DataFramea DatetimeIndex、 awindow的 timedelta-convertible 和( GH 15305 )min_periods >= 1

  • DataFrame.groupby当键数等于 groupby 轴上的元素数时,无法正确识别索引和列键的错误( GH 16859

  • groupby.nunique()无法正确TimeGrouper处理的错误NaTGH 17575

  • DataFrame.groupby意外排序的单个级别选择的错误MultiIndexGH 17537

  • 使用对象覆盖不明确的列名称DataFrame.groupby时引发虚假警告的错误( GH 17383Grouper

  • TimeGrouper作为列表和标量传递时的错误有所不同( GH 17530

稀疏#

  • 当字典作为数据传入时会SparseSeries引发错误( GH 16905AttributeError

  • SparseDataFrame.fillna()从 SciPy 稀疏矩阵实例化框架时未填充所有 NaN 的错误( GH 16112 )

  • 错误SparseSeries.unstack()SparseDataFrame.stack()GH 16614GH 15045

  • make_sparse()处理两个具有相同位的数字/布尔数据时出现错误,当数组dtypeobjectGH 17574)时相同

  • SparseArray.all()现在SparseArray.any()已实施来处理SparseArray,这些已使用但未实施(GH 17570

重塑#

  • 加入/合并非唯一的PeriodIndex凸起 a TypeError( GH 16871 )

  • crosstab()将非对齐整数系列转换为浮点数的错误( GH 17005

  • 与带有 datetimelikes 的分类数据类型合并时出现的错误错误地引发了TypeError( GH 16900 )

  • isin()在大型对象系列和大型比较数组上使用时出现错误( GH 16012

  • 修复了 0.20 的回归,Series.aggregate()DataFrame.aggregate()再次允许字典作为返回值 ( GH 16741 )

  • 使用整数 dtype 输入修复结果的 dtype,从pivot_table()使用margins=True( GH 17013 )调用时开始

  • crosstab()传递两个Series同名的错误引发了KeyError( GH 13279 )

  • Series.argmin()Series.argmax()、 以及它们在DataFrame和 groupby 对象上的对应项可以正确处理包含无限值的浮点数据 ( GH 13595 )。

  • unique()检查字符串元组时出现的错误引发了TypeError( GH 17108 )

  • concat()如果结果索引包含不可比较的元素,则结果索引的顺序是不可预测的错误( GH 17344

  • 修复了在具有值的datetime64数据类型上按多列排序时的回归(GH 16836SeriesNaT

  • pivot_table()结果列未保留columns何时dropna的分类数据类型的错误FalseGH 17842

  • DataFrame.drop_duplicates删除非唯一列名时出现的错误引发了ValueError( GH 17836 )

  • unstack()当在级别列表上调用时,会丢弃参数的错误fillnaGH 13971

  • range对象和其他类似列表的对齐中的错误DataFrame导致操作按行而不是按列执行(GH 17901

数字#

  • Bug in .clip()with并传递了axis=1类似列表的 for ;threshold之前提出过这个问题ValueErrorGH 15390

  • Series.clip()现在DataFrame.clip()将上限和下限参数的 NA 值视为而None不是提升ValueErrorGH 17276)。

分类#

  • Series.isin()使用分类调用时出现错误( GH 16639

  • 具有空值和类别的分类构造函数中的错误导致 为.categories空而不是具有对象 dtype 的Float64Index空( GH 17248Index

  • Series.cat的分类操作中的错误不保留原始系列的名称(GH 17509

  • DataFrame.merge()具有布尔/int 数据类型的分类列失败的错误( GH 17187

  • 当指定的类型为分类类型时,构造Categorical/时出现错误( GH 17884)。CategoricalDtypecategories

pypy #

其他

  • 某些就地运算符在调用时未包装并生成副本的错误(GH 12962

  • 错误处理参数eval()的地方(GH 16732inplace

贡献者#

共有 206 人为此版本贡献了补丁。名字带有“+”的人首次贡献了补丁。

  • 3553x+

  • 亚伦·巴伯

  • 亚当·格利夫 +

  • 亚当·斯密 +

  • 亚当·沙姆连 +

  • 阿德里安·廖 +

  • 艾伦·贝拉斯科 +

  • 易艾伦 +

  • 亚历克斯·B+

  • 亚历克斯·拉伯克 +

  • 亚历克斯·马尔琴科 +

  • 亚历克斯·雷奇克 +

  • 阿莫尔K+

  • 安德烈亚斯·温克勒

  • 安德鲁+

  • 安德鲁亮

  • 安德烈·乔纳森 +

  • 贝基·斯威格

  • 伯凯+

  • 鲍勃·哈夫纳 +

  • 布兰杨

  • 涂布莱恩 +

  • 布洛克·孟德尔 +

  • 卡罗尔·威林 +

  • 卡特·格林+

  • 钱基·帕塔克 +

  • 克里斯

  • 克里斯·比林顿

  • 克里斯·费洛·戈尔戈莱夫斯基 +

  • 克里斯·克尔

  • 克里斯·M+

  • 克里斯·马祖洛 +

  • 克里斯蒂安·普里诺斯

  • 克里斯蒂安·斯塔德-舒尔特

  • 克里斯托夫·莫尔 +

  • 帝斯曼

  • 陈丹尼尔+

  • 丹尼尔·格雷迪

  • 丹尼尔·希梅尔斯坦

  • 戴夫·威尔默

  • 大卫·库克

  • 大卫·格温

  • 大卫·里德 +

  • 狄龙·尼德胡特 +

  • 道格拉斯·拉德

  • 埃里克·斯坦 +

  • 埃里克·维塞尔 +

  • 埃里克·弗雷德里克森

  • 弗洛里安·威廉 +

  • 弗洛里斯·金特 +

  • 禁忌甜甜圈

  • 加布F+

  • 吉夫林+

  • 吉夫林·拉贾亚 +

  • 朱利奥·佩佩 +

  • 吉列尔梅·贝尔特拉米尼

  • 吉列姆·博雷尔 +

  • 秦汉民 +

  • 亨德里克·马凯特 +

  • 于格·瓦卢瓦

  • 侯赛因·坦博利 +

  • 伊娃·米霍利克 +

  • 扬·诺沃特尼 +

  • 简·鲁道夫

  • 让·赫利 +

  • 让-巴蒂斯特·斯基拉蒂 +

  • 让·马蒂厄·德舍内

  • 杰夫·克努普 +

  • 杰夫·雷巴克

  • 杰夫·特拉特纳

  • 珍娜·维吉斯特

  • 吉姆·斯特恩斯206

  • 乔尔·诺斯曼

  • 约翰·W·奥布莱恩

  • 乔恩·克拉尔 +

  • 乔恩·米斯

  • 乔纳森·J·赫尔姆斯 +

  • 乔里斯·范登博什

  • 约瑟夫·瓦格纳

  • 华雷斯·博奇

  • 朱利安·库尔曼 +

  • 卡雷尔·德·布拉班德尔

  • 卡珊德拉·基顿 +

  • 凯隆·皮齐 +

  • 基思·韦伯

  • 克恩克

  • 凯文·谢泼德

  • 柯克·汉森 +

  • 竹内光 +

  • 卢卡斯·库什纳 +

  • 马赫迪·本·杰鲁尔 +

  • 马卡洛夫安德烈+

  • 马尔戈扎塔·图赞斯卡 +

  • 马克·加西亚 +

  • 施玛格丽特 +

  • 火星人 +

  • 马特·巴克+

  • 马修·罗斯克

  • 马蒂·皮库斯

  • 穆罕默德·阿里·“马里”·阿克马纳尔普

  • 迈克尔·加沃达 +

  • 迈克尔·彭科夫 +

  • 米洛+

  • 摩根斯图尔特+

  • 摩根243 +

  • 内森·福特+

  • 尼克·尤班克

  • 尼克·加维 +

  • 奥列格·施坦布克 +

  • P-蒂尔曼+

  • 潘卡·潘迪

  • 帕特里克·罗

  • 帕特里克·奥美斯

  • 保罗·雷迪 +

  • 保拉+

  • 彼得·夸肯布什

  • 彼得·亚诺维奇 +

  • 菲利普·克劳德

  • 皮埃尔·海西格

  • 彼得罗·巴蒂斯顿

  • 普拉杜姆纳·雷迪·钦塔拉

  • 普拉桑吉特·普拉卡什

  • 罗宾五字

  • 瑞安亨德里克森

  • 符山姆

  • 尹尚雄 +

  • 西蒙·吉本斯 +

  • 西蒙·巴伦

  • 史蒂文·卡廷+

  • 苏迪普 +

  • 西尔维娅+

  • TN+

  • 泰尔特

  • 托马斯·卡斯威尔

  • 蒂姆·斯瓦斯特 +

  • 汤姆·奥格斯普格

  • 申通

  • 团+

  • 乌特卡什·乌帕德耶 +

  • 文森特·拉+

  • 维维克+

  • 王爱勇

  • 沃贝尔

  • 韦斯·麦金尼

  • XF+

  • 刘毅+

  • 中林洋介 +

  • 亚伦315 +

  • 巴伯4gh +

  • 阿恩隆德 +

  • 阿古斯丁·门德斯 +

  • 安迪马赫什+

  • ante328 +

  • 阿维奥洛夫+

  • 布普拉加斯蒂斯

  • 贝尔蒂纳托 +

  • 克劳斯+

  • 切恩里克

  • 克里斯-B1

  • 德卡姆+

  • 德韦克内菲克

  • 经济

  • 法克+

  • fding253 +

  • 格菲扬

  • 盖戈德伯格 +

  • 呼呼+

  • 华帅+

  • 伊安

  • 尤利亚+

  • 贾里德斯奈德

  • 杰布罗克门德尔 +

  • 伊德谢内斯

  • 杰博+

  • jschendel +

  • 庆泽田

  • 内核+

  • 猕猴桃+

  • 凯福德

  • 线BP

  • 劳埃德柯克

  • 路易斯波托克 +

  • 麻将+

  • 马尼克班达里 +

  • 玛戈菲尼克斯 +

  • 马蒂亚舒施勒 +

  • 马蒂普

  • 米爱12 +

  • 马尔滕森+

  • pandas-docs-bot +

  • 帕奇德-1 +

  • 菲利法内曼 +

  • rdk1024+

  • 雷迪-p+

  • 里938

  • 瑞安+

  • 维尔尼卡+

  • s-韦根+

  • 斯科特瓦德92 +

  • 斯克白细胞+

  • 步骤4我+

  • 托比奶酪+

  • 礼帽-123 +

  • 茨德洛弗尔

  • 于绍 +

  • zz高+