/changelogs/pandas/pandas-2-to-3
pandas 2 to 3: Copy-on-Write, the str dtype and other breaking changes
verified onenvironmentlocal · windows 10.0.26200 arm64 · GNU bash 5.3.15 (Git Bash)updated 2026-10-20
- tool
- pandas
- versions
- 2.x → 3.0
pandas 3.0.0 was released on 2026-01-21 (3.0.6 on 2026-09-17). Two changes affect most code: Copy-on-Write is now the only behaviour, so any subset or method result behaves as a copy, and string data gets a dedicated str dtype instead of object. The project recommends upgrading to pandas 2.3 first, which warns about most affected patterns.
Strings: object becomes str
cat > dtypes.py <<'PY'
import pandas as pd
s = pd.Series(["a", "b", None])
print("pandas", pd.__version__, "-> dtype:", s.dtype, "| missing value:", repr(s[2]))
PY
uv run -q --no-project --python 3.13 --with pandas==2.2.3 python dtypes.py
python dtypes.pyOutput
pandas 2.2.3 -> dtype: object | missing value: None pandas 3.0.6 -> dtype: str | missing value: nan
The str dtype only holds strings or missing values, and its missing value is NaN. Code that checks dtype == object, or stores non-strings in a text column, needs changes.
Copy-on-Write: chained assignment stops working
cat > chained.py <<'PY'
import warnings, pandas as pd
warnings.simplefilter("ignore")
df = pd.DataFrame({"a": [1, 2, 3], "b": [10, 20, 30]})
df["b"][df["a"] > 1] = 0 # chained assignment
print("pandas", pd.__version__, "-> b:", df["b"].tolist())
PY
uv run -q --no-project --python 3.13 --with pandas==2.2.3 python chained.py
python chained.pyOutput
pandas 2.2.3 -> b: [10, 0, 0] pandas 3.0.6 -> b: [10, 20, 30]
In pandas 2.2 (without Copy-on-Write enabled) the chained assignment changed df; in pandas 3 it never does. Use df.loc[df["a"] > 1, "b"] = 0.
Other changes to check
- Python 3.11+ is required; minimum versions of NumPy and optional dependencies were raised.
- Datetime resolution is inferred from the input instead of always nanoseconds.
- Removed deprecations: everything deprecated during 2.x is gone; run your code on pandas 2.3 with warnings enabled to find it.
- Fewer defensive copies:
.copy()calls added to silenceSettingWithCopyWarningare no longer needed.
Upgrade path
- Upgrade to pandas 2.3 and run tests with
-W error::FutureWarning -W error::DeprecationWarning. - Optionally enable the new behaviour early on 2.x:
pd.options.mode.copy_on_write = Trueandpd.options.future.infer_string = True. - Upgrade to 3.0 and fix remaining
dtype == objectchecks.
Sources
Related pages
errors · pandasSettingWithCopyWarning: A value is trying to be set on a copy of a slicepandas 2 warns SettingWithCopyWarning when you assign to a filtered DataFrame that may be a copy. Use .loc on the original or .copy(); pandas 3 removed it.flags · pandaspandas read_csv low_memory and DtypeWarning: Columns have mixed typesread_csv parses big files in chunks; when chunks infer different types it warns DtypeWarning: Columns have mixed types. Set dtype or use low_memory=False.compat · numpyNumPy versions and supported Python versions (2.0 to 2.5)Python versions supported by each NumPy release: 2.0 runs on 3.9-3.12, 2.1 and 2.2 on 3.10-3.13, 2.4 on 3.11-3.14 and 2.5 on 3.12-3.14, per the release notes.