Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Remove Copy-on-Write warning mode #57234

Merged
merged 1 commit into from
Feb 4, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 0 additions & 5 deletions pandas/_config/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@
"option_context",
"options",
"using_copy_on_write",
"warn_copy_on_write",
]
from pandas._config import config
from pandas._config import dates # pyright: ignore[reportUnusedImport] # noqa: F401
Expand All @@ -35,10 +34,6 @@ def using_copy_on_write() -> bool:
return True


def warn_copy_on_write() -> bool:
return False


def using_nullable_dtypes() -> bool:
_mode_options = _global_config["mode"]
return _mode_options["nullable_dtypes"]
Expand Down
15 changes: 1 addition & 14 deletions pandas/core/frame.py
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,6 @@
from pandas._config import (
get_option,
using_copy_on_write,
warn_copy_on_write,
)

from pandas._libs import (
Expand All @@ -64,7 +63,6 @@
_chained_assignment_method_msg,
_chained_assignment_msg,
_chained_assignment_warning_method_msg,
_chained_assignment_warning_msg,
)
from pandas.util._decorators import (
Appender,
Expand Down Expand Up @@ -4199,17 +4197,6 @@ def __setitem__(self, key, value) -> None:
warnings.warn(
_chained_assignment_msg, ChainedAssignmentError, stacklevel=2
)
elif not PYPY and not using_copy_on_write():
if sys.getrefcount(self) <= 3 and (
warn_copy_on_write()
or (
not warn_copy_on_write()
and any(b.refs.has_reference() for b in self._mgr.blocks)
)
):
warnings.warn(
_chained_assignment_warning_msg, FutureWarning, stacklevel=2
)

key = com.apply_if_callable(key, self)

Expand Down Expand Up @@ -4550,7 +4537,7 @@ def _clear_item_cache(self) -> None:

def _get_item_cache(self, item: Hashable) -> Series:
"""Return the cached item, item represents a label indexer."""
if using_copy_on_write() or warn_copy_on_write():
if using_copy_on_write():
loc = self.columns.get_loc(item)
return self._ixs(loc, axis=1)

Expand Down
112 changes: 2 additions & 110 deletions pandas/core/generic.py
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,6 @@
from pandas._config import (
config,
using_copy_on_write,
warn_copy_on_write,
)

from pandas._libs import lib
Expand Down Expand Up @@ -105,7 +104,6 @@
from pandas.errors.cow import (
_chained_assignment_method_msg,
_chained_assignment_warning_method_msg,
_check_cacher,
)
from pandas.util._decorators import (
deprecate_nonkeyword_arguments,
Expand Down Expand Up @@ -4401,7 +4399,7 @@ def _check_setitem_copy(self, t: str = "setting", force: bool_t = False) -> None
df.iloc[0:5]['group'] = 'a'

"""
if using_copy_on_write() or warn_copy_on_write():
if using_copy_on_write():
return

# return early if the check is not needed
Expand Down Expand Up @@ -7250,22 +7248,6 @@ def fillna(
ChainedAssignmentError,
stacklevel=2,
)
elif (
not PYPY
and not using_copy_on_write()
and self._is_view_after_cow_rules()
):
ctr = sys.getrefcount(self)
ref_count = REF_COUNT
if isinstance(self, ABCSeries) and _check_cacher(self):
# see https://github.com/pandas-dev/pandas/pull/56060#discussion_r1399245221
ref_count += 1
if ctr <= ref_count:
warnings.warn(
_chained_assignment_warning_method_msg,
FutureWarning,
stacklevel=2,
)

value, method = validate_fillna_kwargs(value, method)
if method is not None:
Expand Down Expand Up @@ -7553,22 +7535,6 @@ def ffill(
ChainedAssignmentError,
stacklevel=2,
)
elif (
not PYPY
and not using_copy_on_write()
and self._is_view_after_cow_rules()
):
ctr = sys.getrefcount(self)
ref_count = REF_COUNT
if isinstance(self, ABCSeries) and _check_cacher(self):
# see https://github.com/pandas-dev/pandas/pull/56060#discussion_r1399245221
ref_count += 1
if ctr <= ref_count:
warnings.warn(
_chained_assignment_warning_method_msg,
FutureWarning,
stacklevel=2,
)

return self._pad_or_backfill(
"ffill",
Expand Down Expand Up @@ -7757,22 +7723,6 @@ def bfill(
ChainedAssignmentError,
stacklevel=2,
)
elif (
not PYPY
and not using_copy_on_write()
and self._is_view_after_cow_rules()
):
ctr = sys.getrefcount(self)
ref_count = REF_COUNT
if isinstance(self, ABCSeries) and _check_cacher(self):
# see https://github.com/pandas-dev/pandas/pull/56060#discussion_r1399245221
ref_count += 1
if ctr <= ref_count:
warnings.warn(
_chained_assignment_warning_method_msg,
FutureWarning,
stacklevel=2,
)

return self._pad_or_backfill(
"bfill",
Expand Down Expand Up @@ -7928,26 +7878,6 @@ def replace(
ChainedAssignmentError,
stacklevel=2,
)
elif (
not PYPY
and not using_copy_on_write()
and self._is_view_after_cow_rules()
):
ctr = sys.getrefcount(self)
ref_count = REF_COUNT
if isinstance(self, ABCSeries) and _check_cacher(self):
# in non-CoW mode, chained Series access will populate the
# `_item_cache` which results in an increased ref count not below
# the threshold, while we still need to warn. We detect this case
# of a Series derived from a DataFrame through the presence of
# checking the `_cacher`
ref_count += 1
if ctr <= ref_count:
warnings.warn(
_chained_assignment_warning_method_msg,
FutureWarning,
stacklevel=2,
)

if not is_bool(regex) and to_replace is not None:
raise ValueError("'to_replace' must be 'None' if 'regex' is not a bool")
Expand Down Expand Up @@ -8378,22 +8308,6 @@ def interpolate(
ChainedAssignmentError,
stacklevel=2,
)
elif (
not PYPY
and not using_copy_on_write()
and self._is_view_after_cow_rules()
):
ctr = sys.getrefcount(self)
ref_count = REF_COUNT
if isinstance(self, ABCSeries) and _check_cacher(self):
# see https://github.com/pandas-dev/pandas/pull/56060#discussion_r1399245221
ref_count += 1
if ctr <= ref_count:
warnings.warn(
_chained_assignment_warning_method_msg,
FutureWarning,
stacklevel=2,
)

axis = self._get_axis_number(axis)

Expand Down Expand Up @@ -10563,7 +10477,6 @@ def _where(
inplace: bool_t = False,
axis: Axis | None = None,
level=None,
warn: bool_t = True,
):
"""
Equivalent to public method `where`, except that `other` is not
Expand Down Expand Up @@ -10694,7 +10607,7 @@ def _where(
# we may have different type blocks come out of putmask, so
# reconstruct the block manager

new_data = self._mgr.putmask(mask=cond, new=other, align=align, warn=warn)
new_data = self._mgr.putmask(mask=cond, new=other, align=align)
result = self._constructor_from_mgr(new_data, axes=new_data.axes)
return self._update_inplace(result)

Expand Down Expand Up @@ -12560,29 +12473,8 @@ def _inplace_method(self, other, op) -> Self:
"""
Wrap arithmetic method to operate inplace.
"""
warn = True
if not PYPY and warn_copy_on_write():
if sys.getrefcount(self) <= REF_COUNT + 2:
# we are probably in an inplace setitem context (e.g. df['a'] += 1)
warn = False

result = op(self, other)

if (
self.ndim == 1
and result._indexed_same(self)
and result.dtype == self.dtype
and not using_copy_on_write()
and not (warn_copy_on_write() and not warn)
):
# GH#36498 this inplace op can _actually_ be inplace.
# Item "BlockManager" of "Union[BlockManager, SingleBlockManager]" has
# no attribute "setitem_inplace"
self._mgr.setitem_inplace( # type: ignore[union-attr]
slice(None), result._values, warn=warn
)
return self

# Delete cacher
self._reset_cacher()

Expand Down
7 changes: 2 additions & 5 deletions pandas/core/groupby/grouper.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,10 +12,7 @@

import numpy as np

from pandas._config import (
using_copy_on_write,
warn_copy_on_write,
)
from pandas._config import using_copy_on_write

from pandas._libs.tslibs import OutOfBoundsDatetime
from pandas.errors import InvalidIndexError
Expand Down Expand Up @@ -962,7 +959,7 @@ def is_in_axis(key) -> bool:
def is_in_obj(gpr) -> bool:
if not hasattr(gpr, "name"):
return False
if using_copy_on_write() or warn_copy_on_write():
if using_copy_on_write():
# For the CoW case, we check the references to determine if the
# series is part of the object
try:
Expand Down
21 changes: 2 additions & 19 deletions pandas/core/indexing.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,10 +13,7 @@

import numpy as np

from pandas._config import (
using_copy_on_write,
warn_copy_on_write,
)
from pandas._config import using_copy_on_write

from pandas._libs.indexing import NDFrameIndexerBase
from pandas._libs.lib import item_from_zerodim
Expand All @@ -28,11 +25,7 @@
InvalidIndexError,
LossySetitemError,
)
from pandas.errors.cow import (
_chained_assignment_msg,
_chained_assignment_warning_msg,
_check_cacher,
)
from pandas.errors.cow import _chained_assignment_msg
from pandas.util._decorators import doc
from pandas.util._exceptions import find_stack_level

Expand Down Expand Up @@ -889,16 +882,6 @@ def __setitem__(self, key, value) -> None:
warnings.warn(
_chained_assignment_msg, ChainedAssignmentError, stacklevel=2
)
elif not PYPY and not using_copy_on_write():
ctr = sys.getrefcount(self.obj)
ref_count = 2
if not warn_copy_on_write() and _check_cacher(self.obj):
# see https://github.com/pandas-dev/pandas/pull/56060#discussion_r1399245221
ref_count += 1
if ctr <= ref_count:
warnings.warn(
_chained_assignment_warning_msg, FutureWarning, stacklevel=2
)

check_dict_or_set_indexers(key)
if isinstance(key, tuple):
Expand Down
Loading
Loading