Skip to content

Commit 8c54f26

Browse files
committed
API: Deprecate renamae_axis and reindex_axis
Closes pandas-dev#17833
1 parent 727ea20 commit 8c54f26

20 files changed

+97
-48
lines changed

doc/source/basics.rst

+5-2
Original file line numberDiff line numberDiff line change
@@ -1201,8 +1201,11 @@ With a DataFrame, you can simultaneously reindex the index and columns:
12011201
df
12021202
df.reindex(index=['c', 'f', 'b'], columns=['three', 'two', 'one'])
12031203
1204-
For convenience, you may utilize the :meth:`~Series.reindex_axis` method, which
1205-
takes the labels and a keyword ``axis`` parameter.
1204+
You may also use ``reindex`` with an ``axis`` keyword:
1205+
1206+
.. ipython:: python
1207+
1208+
df.reindex(index=['c', 'f', 'b'], axis='index')
12061209
12071210
Note that the ``Index`` objects containing the actual axis labels can be
12081211
**shared** between objects. So if we have a Series and a DataFrame, the

doc/source/whatsnew/v0.21.0.txt

+2
Original file line numberDiff line numberDiff line change
@@ -810,6 +810,8 @@ Deprecations
810810
- ``.get_value`` and ``.set_value`` on ``Series``, ``DataFrame``, ``Panel``, ``SparseSeries``, and ``SparseDataFrame`` are deprecated in favor of using ``.iat[]`` or ``.at[]`` accessors (:issue:`15269`)
811811
- Passing a non-existent column in ``.to_excel(..., columns=)`` is deprecated and will raise a ``KeyError`` in the future (:issue:`17295`)
812812
- ``raise_on_error`` parameter to :func:`Series.where`, :func:`Series.mask`, :func:`DataFrame.where`, :func:`DataFrame.mask` is deprecated, in favor of ``errors=`` (:issue:`14968`)
813+
- Using :meth:`DataFrame.rename_axis` and :meth:`Series.rename_axis` to alter index or column *labels* is now deprecated in favor of using ``.rename``. ``rename_axis`` may still be used to alter the name of the index or columns (:issue:`17833`).
814+
- :meth:`~NDFrame.reindex_axis` has been deprecated in favor of :meth:`~NDFrame.reindex`. See :ref`here` <whatsnew_0210.enhancements.rename_reindex_axis> for more (:issue:`17833`).
813815

814816
.. _whatsnew_0210.deprecations.select:
815817

pandas/core/computation/align.py

+2-5
Original file line numberDiff line numberDiff line change
@@ -89,6 +89,7 @@ def _align_core(terms):
8989
for axis, items in zip(range(ndim), axes):
9090
ti = terms[i].value
9191

92+
# TODO: handle this for when reindex_axis is removed...
9293
if hasattr(ti, 'reindex_axis'):
9394
transpose = isinstance(ti, pd.Series) and naxes > 1
9495
reindexer = axes[naxes - 1] if transpose else items
@@ -104,11 +105,7 @@ def _align_core(terms):
104105
).format(axis=axis, term=terms[i].name, ordm=ordm)
105106
warnings.warn(w, category=PerformanceWarning, stacklevel=6)
106107

107-
if transpose:
108-
f = partial(ti.reindex, index=reindexer, copy=False)
109-
else:
110-
f = partial(ti.reindex_axis, reindexer, axis=axis,
111-
copy=False)
108+
f = partial(ti.reindex, reindexer, axis=axis, copy=False)
112109

113110
terms[i].update(f())
114111

pandas/core/frame.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -2736,7 +2736,7 @@ def reindexer(value):
27362736
if isinstance(loc, (slice, Series, np.ndarray, Index)):
27372737
cols = maybe_droplevels(self.columns[loc], key)
27382738
if len(cols) and not cols.equals(value.columns):
2739-
value = value.reindex_axis(cols, axis=1)
2739+
value = value.reindex(cols, axis=1)
27402740
# now align rows
27412741
value = reindexer(value).T
27422742

pandas/core/generic.py

+27-17
Original file line numberDiff line numberDiff line change
@@ -129,7 +129,7 @@ def __init__(self, data, axes=None, copy=False, dtype=None,
129129

130130
if axes is not None:
131131
for i, ax in enumerate(axes):
132-
data = data.reindex_axis(ax, axis=i)
132+
data = data.reindex(ax, axis=i)
133133

134134
object.__setattr__(self, 'is_copy', None)
135135
object.__setattr__(self, '_data', data)
@@ -893,17 +893,12 @@ def f(x):
893893
rename.__doc__ = _shared_docs['rename']
894894

895895
def rename_axis(self, mapper, axis=0, copy=True, inplace=False):
896-
"""
897-
Alter index and / or columns using input function or functions.
898-
A scalar or list-like for ``mapper`` will alter the ``Index.name``
899-
or ``MultiIndex.names`` attribute.
900-
A function or dict for ``mapper`` will alter the labels.
901-
Function / dict values must be unique (1-to-1). Labels not contained in
902-
a dict / Series will be left as-is.
896+
"""Alter the name of the index or columns.
903897
904898
Parameters
905899
----------
906-
mapper : scalar, list-like, dict-like or function, optional
900+
mapper : scalar, list-like, optional
901+
Value to set the axis name attribute.
907902
axis : int or string, default 0
908903
copy : boolean, default True
909904
Also copy underlying data
@@ -913,6 +908,13 @@ def rename_axis(self, mapper, axis=0, copy=True, inplace=False):
913908
-------
914909
renamed : type of caller or None if inplace=True
915910
911+
Notes
912+
-----
913+
Prior to version 0.21.0, ``rename_axis`` could also be used to change
914+
the axis *labels* by passing a mapping or scalar. This behavior is
915+
deprecated and will be removed in a future version. Use ``rename``
916+
instead.
917+
916918
See Also
917919
--------
918920
pandas.NDFrame.rename
@@ -922,29 +924,29 @@ def rename_axis(self, mapper, axis=0, copy=True, inplace=False):
922924
--------
923925
924926
>>> df = pd.DataFrame({"A": [1, 2, 3], "B": [4, 5, 6]})
925-
>>> df.rename_axis("foo") # scalar, alters df.index.name
927+
>>> df.rename_axis("foo")
926928
A B
927929
foo
928930
0 1 4
929931
1 2 5
930932
2 3 6
931-
>>> df.rename_axis(lambda x: 2 * x) # function: alters labels
932-
A B
933-
0 1 4
934-
2 2 5
935-
4 3 6
936-
>>> df.rename_axis({"A": "ehh", "C": "see"}, axis="columns") # mapping
937-
ehh B
933+
934+
>>> df.rename_axis("bar", axis="columns")
935+
bar A B
938936
0 1 4
939937
1 2 5
940938
2 3 6
939+
941940
"""
942941
inplace = validate_bool_kwarg(inplace, 'inplace')
943942
non_mapper = is_scalar(mapper) or (is_list_like(mapper) and not
944943
is_dict_like(mapper))
945944
if non_mapper:
946945
return self._set_axis_name(mapper, axis=axis, inplace=inplace)
947946
else:
947+
msg = ("Using 'rename_axis' to alter labels is deprecated. "
948+
"Use '.rename' instead")
949+
warnings.warn(msg, FutureWarning, stacklevel=2)
948950
axis = self._get_axis_name(axis)
949951
d = {'copy': copy, 'inplace': inplace}
950952
d[axis] = mapper
@@ -2981,6 +2983,11 @@ def reindex(self, *args, **kwargs):
29812983
tolerance = kwargs.pop('tolerance', None)
29822984
fill_value = kwargs.pop('fill_value', np.nan)
29832985

2986+
# Series.reindex doesn't use / need the axis kwarg
2987+
# We pop and ignore it here, to make writing Series/Frame generic code
2988+
# easier
2989+
kwargs.pop("axis", None)
2990+
29842991
if kwargs:
29852992
raise TypeError('reindex() got an unexpected keyword '
29862993
'argument "{0}"'.format(list(kwargs.keys())[0]))
@@ -3085,11 +3092,14 @@ def _reindex_multi(self, axes, copy, fill_value):
30853092
@Appender(_shared_docs['reindex_axis'] % _shared_doc_kwargs)
30863093
def reindex_axis(self, labels, axis=0, method=None, level=None, copy=True,
30873094
limit=None, fill_value=np.nan):
3095+
msg = ("'.reindex_axis' is deprecated and will be removed in a future "
3096+
"version. Use '.reindex' instead.")
30883097
self._consolidate_inplace()
30893098

30903099
axis_name = self._get_axis_name(axis)
30913100
axis_values = self._get_axis(axis_name)
30923101
method = missing.clean_reindex_fill_method(method)
3102+
warnings.warn(msg, FutureWarning, stacklevel=3)
30933103
new_index, indexer = axis_values.reindex(labels, method, level,
30943104
limit=limit)
30953105
return self._reindex_with_indexers({axis: [new_index, indexer]},

pandas/core/groupby.py

+2-2
Original file line numberDiff line numberDiff line change
@@ -901,7 +901,7 @@ def reset_identity(values):
901901
result.index.get_indexer_for(ax.values))
902902
result = result.take(indexer, axis=self.axis)
903903
else:
904-
result = result.reindex_axis(ax, axis=self.axis)
904+
result = result.reindex(ax, axis=self.axis)
905905

906906
elif self.group_keys:
907907

@@ -4580,7 +4580,7 @@ def _get_sorted_data(self):
45804580

45814581
# this is sort of wasteful but...
45824582
sorted_axis = data.axes[self.axis].take(self.sort_idx)
4583-
sorted_data = data.reindex_axis(sorted_axis, axis=self.axis)
4583+
sorted_data = data.reindex(sorted_axis, axis=self.axis)
45844584

45854585
return sorted_data
45864586

pandas/core/indexing.py

+2-2
Original file line numberDiff line numberDiff line change
@@ -368,7 +368,7 @@ def _setitem_with_indexer(self, indexer, value):
368368
# so the object is the same
369369
index = self.obj._get_axis(i)
370370
labels = index.insert(len(index), key)
371-
self.obj._data = self.obj.reindex_axis(labels, i)._data
371+
self.obj._data = self.obj.reindex(labels, axis=i)._data
372372
self.obj._maybe_update_cacher(clear=True)
373373
self.obj.is_copy = None
374374

@@ -1132,7 +1132,7 @@ def _getitem_iterable(self, key, axis=None):
11321132
if labels.is_unique and Index(keyarr).is_unique:
11331133

11341134
try:
1135-
return self.obj.reindex_axis(keyarr, axis=axis)
1135+
return self.obj.reindex(keyarr, axis=axis)
11361136
except AttributeError:
11371137

11381138
# Series

pandas/core/internals.py

+2-2
Original file line numberDiff line numberDiff line change
@@ -3283,8 +3283,8 @@ def apply(self, f, axes=None, filter=None, do_integrity_check=False,
32833283

32843284
for k, obj in aligned_args.items():
32853285
axis = getattr(obj, '_info_axis_number', 0)
3286-
kwargs[k] = obj.reindex_axis(b_items, axis=axis,
3287-
copy=align_copy)
3286+
kwargs[k] = obj.reindex(b_items, axis=axis,
3287+
copy=align_copy)
32883288

32893289
kwargs['mgr'] = self
32903290
applied = getattr(b, f)(**kwargs)

pandas/core/panel.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -722,7 +722,7 @@ def dropna(self, axis=0, how='any', inplace=False):
722722
cond = mask == per_slice
723723

724724
new_ax = self._get_axis(axis)[cond]
725-
result = self.reindex_axis(new_ax, axis=axis)
725+
result = self.reindex(new_ax, axis=axis)
726726
if inplace:
727727
self._update_inplace(result)
728728
else:

pandas/core/reshape/pivot.py

+2-2
Original file line numberDiff line numberDiff line change
@@ -101,14 +101,14 @@ def pivot_table(data, values=None, index=None, columns=None, aggfunc='mean',
101101
try:
102102
m = MultiIndex.from_arrays(cartesian_product(table.index.levels),
103103
names=table.index.names)
104-
table = table.reindex_axis(m, axis=0)
104+
table = table.reindex(m, axis=0)
105105
except AttributeError:
106106
pass # it's a single level
107107

108108
try:
109109
m = MultiIndex.from_arrays(cartesian_product(table.columns.levels),
110110
names=table.columns.names)
111-
table = table.reindex_axis(m, axis=1)
111+
table = table.reindex(m, axis=1)
112112
except AttributeError:
113113
pass # it's a single level or a series
114114

pandas/core/series.py

+4
Original file line numberDiff line numberDiff line change
@@ -2615,6 +2615,10 @@ def reindex_axis(self, labels, axis=0, **kwargs):
26152615
""" for compatibility with higher dims """
26162616
if axis != 0:
26172617
raise ValueError("cannot reindex series on non-zero axis!")
2618+
msg = ("'.reindex_axis' is deprecated and will be removed in a future "
2619+
"version. Use '.reindex' instead.")
2620+
warnings.warn(msg, FutureWarning, stacklevel=2)
2621+
26182622
return self.reindex(index=labels, **kwargs)
26192623

26202624
def memory_usage(self, index=True, deep=False):

pandas/core/sparse/scipy_sparse.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -134,5 +134,5 @@ def _coo_to_sparse_series(A, dense_index=False):
134134
i = range(A.shape[0])
135135
j = range(A.shape[1])
136136
ind = MultiIndex.from_product([i, j])
137-
s = s.reindex_axis(ind)
137+
s = s.reindex(ind)
138138
return s

pandas/io/pytables.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -1040,7 +1040,7 @@ def append_to_multiple(self, d, value, selector, data_columns=None,
10401040
dc = data_columns if k == selector else None
10411041

10421042
# compute the val
1043-
val = value.reindex_axis(v, axis=axis)
1043+
val = value.reindex(v, axis=axis)
10441044

10451045
self.append(k, val, data_columns=dc, **kwargs)
10461046

pandas/plotting/_core.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -697,7 +697,7 @@ def _parse_errorbars(self, label, err):
697697
from pandas import DataFrame, Series
698698

699699
def match_labels(data, e):
700-
e = e.reindex_axis(data.index)
700+
e = e.reindex(data.index)
701701
return e
702702

703703
# key-matched DataFrame

pandas/tests/frame/test_alter_axes.py

+19
Original file line numberDiff line numberDiff line change
@@ -436,6 +436,25 @@ def test_rename_axis_inplace(self):
436436
assert no_return is None
437437
assert_frame_equal(result, expected)
438438

439+
def test_rename_axis_warns(self):
440+
# https://github.com/pandas-dev/pandas/issues/17833
441+
df = pd.DataFrame({"A": [1, 2], "B": [1, 2]})
442+
with tm.assert_produces_warning(FutureWarning) as w:
443+
df.rename_axis(id, axis=0)
444+
assert 'rename' in str(w[0].message)
445+
446+
with tm.assert_produces_warning(FutureWarning) as w:
447+
df.rename_axis({0: 10, 1: 20}, axis=0)
448+
assert 'rename' in str(w[0].message)
449+
450+
with tm.assert_produces_warning(FutureWarning) as w:
451+
df.rename_axis(id, axis=1)
452+
assert 'rename' in str(w[0].message)
453+
454+
with tm.assert_produces_warning(FutureWarning) as w:
455+
df['A'].rename_axis(id)
456+
assert 'rename' in str(w[0].message)
457+
439458
def test_rename_multiindex(self):
440459

441460
tuples_index = [('foo1', 'bar1'), ('foo2', 'bar2')]

pandas/tests/frame/test_axis_select_reindex.py

+13-5
Original file line numberDiff line numberDiff line change
@@ -418,11 +418,13 @@ def test_reindex_fill_value(self):
418418
assert_frame_equal(result, expected)
419419

420420
# reindex_axis
421-
result = df.reindex_axis(lrange(15), fill_value=0., axis=0)
421+
with tm.assert_produces_warning(FutureWarning):
422+
result = df.reindex_axis(lrange(15), fill_value=0., axis=0)
422423
expected = df.reindex(lrange(15)).fillna(0)
423424
assert_frame_equal(result, expected)
424425

425-
result = df.reindex_axis(lrange(5), fill_value=0., axis=1)
426+
with tm.assert_produces_warning(FutureWarning):
427+
result = df.reindex_axis(lrange(5), fill_value=0., axis=1)
426428
expected = df.reindex(columns=lrange(5)).fillna(0)
427429
assert_frame_equal(result, expected)
428430

@@ -1030,20 +1032,26 @@ def test_reindex_corner(self):
10301032

10311033
def test_reindex_axis(self):
10321034
cols = ['A', 'B', 'E']
1033-
reindexed1 = self.intframe.reindex_axis(cols, axis=1)
1035+
with tm.assert_produces_warning(FutureWarning) as m:
1036+
reindexed1 = self.intframe.reindex_axis(cols, axis=1)
1037+
assert 'reindex' in str(m[0].message)
10341038
reindexed2 = self.intframe.reindex(columns=cols)
10351039
assert_frame_equal(reindexed1, reindexed2)
10361040

10371041
rows = self.intframe.index[0:5]
1038-
reindexed1 = self.intframe.reindex_axis(rows, axis=0)
1042+
with tm.assert_produces_warning(FutureWarning) as m:
1043+
reindexed1 = self.intframe.reindex_axis(rows, axis=0)
1044+
assert 'reindex' in str(m[0].message)
10391045
reindexed2 = self.intframe.reindex(index=rows)
10401046
assert_frame_equal(reindexed1, reindexed2)
10411047

10421048
pytest.raises(ValueError, self.intframe.reindex_axis, rows, axis=2)
10431049

10441050
# no-op case
10451051
cols = self.frame.columns.copy()
1046-
newFrame = self.frame.reindex_axis(cols, axis=1)
1052+
with tm.assert_produces_warning(FutureWarning) as m:
1053+
newFrame = self.frame.reindex_axis(cols, axis=1)
1054+
assert 'reindex' in str(m[0].message)
10471055
assert_frame_equal(newFrame, self.frame)
10481056

10491057
def test_reindex_with_nans(self):

pandas/tests/reshape/test_reshape.py

+3-3
Original file line numberDiff line numberDiff line change
@@ -311,7 +311,7 @@ def test_include_na(self):
311311
'a': {0: 1, 1: 0, 2: 0},
312312
'b': {0: 0, 1: 1, 2: 0}},
313313
dtype=np.uint8)
314-
exp_na = exp_na.reindex_axis(['a', 'b', nan], 1)
314+
exp_na = exp_na.reindex(['a', 'b', nan], axis=1)
315315
# hack (NaN handling in assert_index_equal)
316316
exp_na.columns = res_na.columns
317317
assert_frame_equal(res_na, exp_na)
@@ -542,8 +542,8 @@ def test_basic_drop_first_NA(self):
542542
2: 0},
543543
nan: {0: 0,
544544
1: 0,
545-
2: 1}}, dtype=np.uint8).reindex_axis(
546-
['b', nan], 1)
545+
2: 1}}, dtype=np.uint8).reindex(
546+
['b', nan], axis=1)
547547
assert_frame_equal(res_na, exp_na)
548548

549549
res_just_na = get_dummies([nan], dummy_na=True, sparse=self.sparse,

pandas/tests/sparse/test_series.py

+6
Original file line numberDiff line numberDiff line change
@@ -1414,6 +1414,12 @@ def test_deprecated_numpy_func_call(self):
14141414
check_stacklevel=False):
14151415
getattr(getattr(self, series), func)()
14161416

1417+
def test_deprecated_reindex_axis(self):
1418+
# https://github.com/pandas-dev/pandas/issues/17833
1419+
with tm.assert_produces_warning(FutureWarning) as m:
1420+
self.bseries.reindex_axis([0, 1, 2])
1421+
assert 'reindex' in str(m[0].message)
1422+
14171423

14181424
@pytest.mark.parametrize(
14191425
'datetime_type', (np.datetime64,

pandas/tests/test_multilevel.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -1805,7 +1805,7 @@ def test_reindex_level_partial_selection(self):
18051805
expected = self.frame.iloc[[0, 1, 2, 7, 8, 9]]
18061806
tm.assert_frame_equal(result, expected)
18071807

1808-
result = self.frame.T.reindex_axis(['foo', 'qux'], axis=1, level=0)
1808+
result = self.frame.T.reindex(['foo', 'qux'], axis=1, level=0)
18091809
tm.assert_frame_equal(result, expected.T)
18101810

18111811
result = self.frame.loc[['foo', 'qux']]

0 commit comments

Comments
 (0)