|
116 | 116 | PeriodArray, |
117 | 117 | TimedeltaArray, |
118 | 118 | ) |
| 119 | +from pandas.core.arrays.string_ import StringDtype |
119 | 120 | from pandas.core.base import PandasObject |
120 | 121 | import pandas.core.common as com |
121 | 122 | from pandas.core.computation import expressions |
@@ -477,7 +478,9 @@ def split_and_operate(self, func, *args, **kwargs) -> list[Block]: |
477 | 478 | # Up/Down-casting |
478 | 479 |
|
479 | 480 | @final |
480 | | - def coerce_to_target_dtype(self, other, warn_on_upcast: bool = False) -> Block: |
| 481 | + def coerce_to_target_dtype( |
| 482 | + self, other, warn_on_upcast: bool = False, using_cow: bool = False |
| 483 | + ) -> Block: |
481 | 484 | """ |
482 | 485 | coerce the current block to a dtype compat for other |
483 | 486 | we will return a block, possibly object, and not raise |
@@ -529,7 +532,14 @@ def coerce_to_target_dtype(self, other, warn_on_upcast: bool = False) -> Block: |
529 | 532 | f"{self.values.dtype}. Please report a bug at " |
530 | 533 | "https://github.com/pandas-dev/pandas/issues." |
531 | 534 | ) |
532 | | - return self.astype(new_dtype, copy=False) |
| 535 | + copy = False |
| 536 | + if ( |
| 537 | + not using_cow |
| 538 | + and isinstance(self.dtype, StringDtype) |
| 539 | + and self.dtype.storage == "python" |
| 540 | + ): |
| 541 | + copy = True |
| 542 | + return self.astype(new_dtype, copy=copy, using_cow=using_cow) |
533 | 543 |
|
534 | 544 | @final |
535 | 545 | def _maybe_downcast( |
@@ -927,12 +937,13 @@ def replace( |
927 | 937 | if value is None or value is NA: |
928 | 938 | blk = self.astype(np.dtype(object)) |
929 | 939 | else: |
930 | | - blk = self.coerce_to_target_dtype(value) |
| 940 | + blk = self.coerce_to_target_dtype(value, using_cow=using_cow) |
931 | 941 | return blk.replace( |
932 | 942 | to_replace=to_replace, |
933 | 943 | value=value, |
934 | 944 | inplace=True, |
935 | 945 | mask=mask, |
| 946 | + using_cow=using_cow, |
936 | 947 | ) |
937 | 948 |
|
938 | 949 | else: |
|
0 commit comments