Skip to content

Commit 4aaadfa

Browse files
resolve merge conflicts
2 parents 7121d9c + 330bede commit 4aaadfa

26 files changed

+137
-71
lines changed

.gitignore

+1
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,7 @@ dist
5757
# wheel files
5858
*.whl
5959
**/wheelhouse/*
60+
pip-wheel-metadata
6061
# coverage
6162
.coverage
6263
coverage.xml

MANIFEST.in

+1
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ include LICENSE
33
include RELEASE.md
44
include README.md
55
include setup.py
6+
include pyproject.toml
67

78
graft doc
89
prune doc/build

Makefile

+1-1
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ black:
1818
black . --exclude '(asv_bench/env|\.egg|\.git|\.hg|\.mypy_cache|\.nox|\.tox|\.venv|_build|buck-out|build|dist|setup.py)'
1919

2020
develop: build
21-
python setup.py develop
21+
python -m pip install --no-build-isolation -e .
2222

2323
doc:
2424
-rm -rf doc/build doc/source/generated

README.md

+6-5
Original file line numberDiff line numberDiff line change
@@ -188,16 +188,17 @@ python setup.py install
188188

189189
or for installing in [development mode](https://pip.pypa.io/en/latest/reference/pip_install.html#editable-installs):
190190

191+
191192
```sh
192-
python setup.py develop
193+
python -m pip install --no-build-isolation -e .
193194
```
194195

195-
Alternatively, you can use `pip` if you want all the dependencies pulled
196-
in automatically (the `-e` option is for installing it in [development
197-
mode](https://pip.pypa.io/en/latest/reference/pip_install.html#editable-installs)):
196+
If you have `make`, you can also use `make develop` to run the same command.
197+
198+
or alternatively
198199

199200
```sh
200-
pip install -e .
201+
python setup.py develop
201202
```
202203

203204
See the full instructions for [installing from source](https://pandas.pydata.org/pandas-docs/stable/install.html#installing-from-source).

ci/incremental/build.cmd

+4-4
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,9 @@
11
@rem https://github.com/numba/numba/blob/master/buildscripts/incremental/build.cmd
22

3-
@rem Build numba extensions without silencing compile errors
4-
python setup.py build_ext -q --inplace
3+
@rem Build extensions
4+
python setup.py build_ext -q -i
55

6-
@rem Install pandas locally
7-
python -m pip install -e .
6+
@rem Install pandas
7+
python -m pip install --no-build-isolation -e .
88

99
if %errorlevel% neq 0 exit /b %errorlevel%

ci/setup_env.sh

+14-3
Original file line numberDiff line numberDiff line change
@@ -115,9 +115,20 @@ conda list pandas
115115

116116
# Make sure any error below is reported as such
117117

118-
echo "Build extensions and install pandas"
119-
python setup.py build_ext -q --inplace
120-
python -m pip install -e .
118+
echo "[Build extensions]"
119+
python setup.py build_ext -q -i
120+
121+
# XXX: Some of our environments end up with old verisons of pip (10.x)
122+
# Adding a new enough verison of pip to the requirements explodes the
123+
# solve time. Just using pip to update itself.
124+
# - py35_macos
125+
# - py35_compat
126+
# - py36_32bit
127+
echo "[Updating pip]"
128+
python -m pip install --no-deps -U pip wheel setuptools
129+
130+
echo "[Install pandas]"
131+
python -m pip install --no-build-isolation -e .
121132

122133
echo
123134
echo "conda list"

doc/source/development/contributing.rst

+2-2
Original file line numberDiff line numberDiff line change
@@ -208,7 +208,7 @@ We'll now kick off a three-step process:
208208
209209
# Build and install pandas
210210
python setup.py build_ext --inplace -j 4
211-
python -m pip install -e .
211+
python -m pip install -e --no-build-isolation .
212212
213213
At this point you should be able to import pandas from your locally built version::
214214

@@ -252,7 +252,7 @@ You'll need to have at least python3.5 installed on your system.
252252
253253
# Build and install pandas
254254
python setup.py build_ext --inplace -j 4
255-
python -m pip install -e .
255+
python -m pip install -e --no-build-isolation .
256256
257257
Creating a branch
258258
-----------------

doc/source/whatsnew/v0.25.2.rst

-1
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,6 @@ Indexing
5252
-
5353
-
5454
-
55-
-
5655

5756
Missing
5857
^^^^^^^

doc/source/whatsnew/v1.0.0.rst

+3-1
Original file line numberDiff line numberDiff line change
@@ -170,6 +170,7 @@ Indexing
170170

171171
- Bug in assignment using a reverse slicer (:issue:`26939`)
172172
- Bug in reindexing a :meth:`PeriodIndex` with another type of index that contained a `Period` (:issue:`28323`) (:issue:`28337`)
173+
- Fix assignment of column via `.loc` with numpy non-ns datetime type (:issue:`27395`)
173174

174175
Missing
175176
^^^^^^^
@@ -226,6 +227,7 @@ Sparse
226227
Build Changes
227228
^^^^^^^^^^^^^
228229
- Fixed pyqt development dependency issue because of different pyqt package name in conda and PyPI (:issue:`26838`)
230+
- Added a `pyproject.toml <https://www.python.org/dev/peps/pep-0517/>`_ file (:issue:`20775`)
229231

230232

231233
ExtensionArray
@@ -240,7 +242,7 @@ Other
240242
- Trying to set the ``display.precision``, ``display.max_rows`` or ``display.max_columns`` using :meth:`set_option` to anything but a ``None`` or a positive int will raise a ``ValueError`` (:issue:`23348`)
241243
- Using :meth:`DataFrame.replace` with overlapping keys in a nested dictionary will no longer raise, now matching the behavior of a flat dictionary (:issue:`27660`)
242244
- :meth:`DataFrame.to_csv` and :meth:`Series.to_csv` now support dicts as ``compression`` argument with key ``'method'`` being the compression method and others as additional compression options when the compression method is ``'zip'``. (:issue:`26023`)
243-
-
245+
- :meth:`Series.append` will no longer raise a ``TypeError`` when passed a tuple of ``Series`` (:issue:`28410`)
244246

245247
.. _whatsnew_1000.contributors:
246248

environment.yml

-4
Original file line numberDiff line numberDiff line change
@@ -82,7 +82,3 @@ dependencies:
8282
- xlwt # pandas.read_excel, DataFrame.to_excel, pandas.ExcelWriter, pandas.ExcelFile
8383
- odfpy # pandas.read_excel
8484
- pyreadstat # pandas.read_spss
85-
86-
# temporarily pin openssl
87-
# https://github.com/pandas-dev/pandas/issues/28402
88-
- openssl=1.1.1c

pandas/core/arrays/sparse.py

+2-2
Original file line numberDiff line numberDiff line change
@@ -245,10 +245,10 @@ def construct_from_string(cls, string):
245245
if string.startswith("Sparse"):
246246
try:
247247
sub_type, has_fill_value = cls._parse_subtype(string)
248-
result = SparseDtype(sub_type)
249-
except Exception:
248+
except ValueError:
250249
raise TypeError(msg)
251250
else:
251+
result = SparseDtype(sub_type)
252252
msg = (
253253
"Could not construct SparseDtype from '{}'.\n\nIt "
254254
"looks like the fill_value in the string is not "

pandas/core/dtypes/cast.py

+8-2
Original file line numberDiff line numberDiff line change
@@ -1029,7 +1029,10 @@ def maybe_cast_to_datetime(value, dtype, errors="raise"):
10291029
)
10301030

10311031
if is_datetime64 and not is_dtype_equal(dtype, _NS_DTYPE):
1032-
if dtype.name in ("datetime64", "datetime64[ns]"):
1032+
1033+
# pandas supports dtype whose granularity is less than [ns]
1034+
# e.g., [ps], [fs], [as]
1035+
if dtype <= np.dtype("M8[ns]"):
10331036
if dtype.name == "datetime64":
10341037
raise ValueError(msg.format(dtype=dtype.name))
10351038
dtype = _NS_DTYPE
@@ -1047,7 +1050,10 @@ def maybe_cast_to_datetime(value, dtype, errors="raise"):
10471050
value = [value]
10481051

10491052
elif is_timedelta64 and not is_dtype_equal(dtype, _TD_DTYPE):
1050-
if dtype.name in ("timedelta64", "timedelta64[ns]"):
1053+
1054+
# pandas supports dtype whose granularity is less than [ns]
1055+
# e.g., [ps], [fs], [as]
1056+
if dtype <= np.dtype("m8[ns]"):
10511057
if dtype.name == "timedelta64":
10521058
raise ValueError(msg.format(dtype=dtype.name))
10531059
dtype = _TD_DTYPE

pandas/core/dtypes/common.py

+2-4
Original file line numberDiff line numberDiff line change
@@ -2051,10 +2051,8 @@ def pandas_dtype(dtype):
20512051
# raise a consistent TypeError if failed
20522052
try:
20532053
npdtype = np.dtype(dtype)
2054-
except Exception:
2055-
# we don't want to force a repr of the non-string
2056-
if not isinstance(dtype, str):
2057-
raise TypeError("data type not understood")
2054+
except SyntaxError:
2055+
# np.dtype uses `eval` which can raise SyntaxError
20582056
raise TypeError("data type '{}' not understood".format(dtype))
20592057

20602058
# Any invalid dtype (such as pd.Timestamp) should raise an error.

pandas/core/ops/__init__.py

+9-7
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,11 @@
4040

4141
from pandas._typing import ArrayLike
4242
from pandas.core.construction import array, extract_array
43-
from pandas.core.ops.array_ops import comp_method_OBJECT_ARRAY, define_na_arithmetic_op
43+
from pandas.core.ops.array_ops import (
44+
comp_method_OBJECT_ARRAY,
45+
define_na_arithmetic_op,
46+
na_arithmetic_op,
47+
)
4448
from pandas.core.ops.docstrings import (
4549
_arith_doc_FRAME,
4650
_flex_comp_doc_FRAME,
@@ -627,12 +631,13 @@ def _arith_method_SERIES(cls, op, special):
627631
_construct_divmod_result if op in [divmod, rdivmod] else _construct_result
628632
)
629633

630-
na_op = define_na_arithmetic_op(op, str_rep, eval_kwargs)
631-
632634
def wrapper(left, right):
633635
if isinstance(right, ABCDataFrame):
634636
return NotImplemented
635637

638+
left, right = _align_method_SERIES(left, right)
639+
res_name = get_op_result_name(left, right)
640+
636641
keep_null_freq = isinstance(
637642
right,
638643
(
@@ -644,9 +649,6 @@ def wrapper(left, right):
644649
),
645650
)
646651

647-
left, right = _align_method_SERIES(left, right)
648-
res_name = get_op_result_name(left, right)
649-
650652
lvalues = extract_array(left, extract_numpy=True)
651653
rvalues = extract_array(right, extract_numpy=True)
652654

@@ -659,7 +661,7 @@ def wrapper(left, right):
659661

660662
else:
661663
with np.errstate(all="ignore"):
662-
result = na_op(lvalues, rvalues)
664+
result = na_arithmetic_op(lvalues, rvalues, op, str_rep, eval_kwargs)
663665

664666
# We do not pass dtype to ensure that the Series constructor
665667
# does inference in the case where `result` has object-dtype.

pandas/core/ops/array_ops.py

+27-21
Original file line numberDiff line numberDiff line change
@@ -98,31 +98,37 @@ def masked_arith_op(x, y, op):
9898

9999
def define_na_arithmetic_op(op, str_rep, eval_kwargs):
100100
def na_op(x, y):
101-
"""
102-
Return the result of evaluating op on the passed in values.
101+
return na_arithmetic_op(x, y, op, str_rep, eval_kwargs)
103102

104-
If native types are not compatible, try coersion to object dtype.
103+
return na_op
105104

106-
Parameters
107-
----------
108-
x : array-like
109-
y : array-like or scalar
110105

111-
Returns
112-
-------
113-
array-like
106+
def na_arithmetic_op(left, right, op, str_rep, eval_kwargs):
107+
"""
108+
Return the result of evaluating op on the passed in values.
114109
115-
Raises
116-
------
117-
TypeError : invalid operation
118-
"""
119-
import pandas.core.computation.expressions as expressions
110+
If native types are not compatible, try coersion to object dtype.
120111
121-
try:
122-
result = expressions.evaluate(op, str_rep, x, y, **eval_kwargs)
123-
except TypeError:
124-
result = masked_arith_op(x, y, op)
112+
Parameters
113+
----------
114+
left : np.ndarray
115+
right : np.ndarray or scalar
116+
str_rep : str or None
117+
eval_kwargs : kwargs to pass to expressions
118+
119+
Returns
120+
-------
121+
array-like
122+
123+
Raises
124+
------
125+
TypeError : invalid operation
126+
"""
127+
import pandas.core.computation.expressions as expressions
125128

126-
return missing.dispatch_fill_zeros(op, x, y, result)
129+
try:
130+
result = expressions.evaluate(op, str_rep, left, right, **eval_kwargs)
131+
except TypeError:
132+
result = masked_arith_op(left, right, op)
127133

128-
return na_op
134+
return missing.dispatch_fill_zeros(op, left, right, result)

pandas/core/series.py

+2-3
Original file line numberDiff line numberDiff line change
@@ -2730,9 +2730,8 @@ def append(self, to_append, ignore_index=False, verify_integrity=False):
27302730
from pandas.core.reshape.concat import concat
27312731

27322732
if isinstance(to_append, (list, tuple)):
2733-
# https://github.com/pandas-dev/pandas/issues/28410
2734-
# error: Unsupported operand types for + ("List[Any]" and "Tuple[Any, ...]")
2735-
to_concat = [self] + to_append # type: ignore
2733+
to_concat = [self]
2734+
to_concat.extend(to_append)
27362735
else:
27372736
to_concat = [self, to_append]
27382737
return concat(

pandas/io/pytables.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -1791,7 +1791,7 @@ def convert(self, values, nan_rep, encoding, errors, start=None, stop=None):
17911791
# making an Index instance could throw a number of different errors
17921792
try:
17931793
self.values = Index(values, **kwargs)
1794-
except Exception: # noqa: E722
1794+
except Exception:
17951795

17961796
# if the output freq is different that what we recorded,
17971797
# it should be None (see also 'doc example part 2')

pandas/tests/dtypes/test_common.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -678,7 +678,7 @@ def test__get_dtype_sparse():
678678
(None, "Cannot deduce dtype from null object"),
679679
(1, "data type not understood"),
680680
(1.2, "data type not understood"),
681-
("random string", "data type 'random string' not understood"),
681+
("random string", 'data type "random string" not understood'),
682682
(pd.DataFrame([1, 2]), "data type not understood"),
683683
],
684684
)

pandas/tests/indexes/interval/test_astype.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ def test_astype_cannot_cast(self, index, dtype):
6767
index.astype(dtype)
6868

6969
def test_astype_invalid_dtype(self, index):
70-
msg = "data type 'fake_dtype' not understood"
70+
msg = 'data type "fake_dtype" not understood'
7171
with pytest.raises(TypeError, match=msg):
7272
index.astype("fake_dtype")
7373

pandas/tests/indexes/interval/test_construction.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -164,7 +164,7 @@ def test_generic_errors(self, constructor):
164164
constructor(dtype="int64", **filler)
165165

166166
# invalid dtype
167-
msg = "data type 'invalid' not understood"
167+
msg = 'data type "invalid" not understood'
168168
with pytest.raises(TypeError, match=msg):
169169
constructor(dtype="invalid", **filler)
170170

pandas/tests/indexing/test_loc.py

+22
Original file line numberDiff line numberDiff line change
@@ -690,6 +690,28 @@ def test_loc_setitem_consistency_slice_column_len(self):
690690
)
691691
tm.assert_series_equal(df[("Respondent", "Duration")], expected)
692692

693+
@pytest.mark.parametrize("unit", ["Y", "M", "D", "h", "m", "s", "ms", "us"])
694+
def test_loc_assign_non_ns_datetime(self, unit):
695+
# GH 27395, non-ns dtype assignment via .loc should work
696+
# and return the same result when using simple assignment
697+
df = DataFrame(
698+
{
699+
"timestamp": [
700+
np.datetime64("2017-02-11 12:41:29"),
701+
np.datetime64("1991-11-07 04:22:37"),
702+
]
703+
}
704+
)
705+
706+
df.loc[:, unit] = df.loc[:, "timestamp"].values.astype(
707+
"datetime64[{unit}]".format(unit=unit)
708+
)
709+
df["expected"] = df.loc[:, "timestamp"].values.astype(
710+
"datetime64[{unit}]".format(unit=unit)
711+
)
712+
expected = Series(df.loc[:, "expected"], name=unit)
713+
tm.assert_series_equal(df.loc[:, unit], expected)
714+
693715
def test_loc_setitem_frame(self):
694716
df = self.frame_labels
695717

pandas/tests/io/parser/test_dtypes.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,7 @@ def test_invalid_dtype_per_column(all_parsers):
7979
3,4.5
8080
4,5.5"""
8181

82-
with pytest.raises(TypeError, match="data type 'foo' not understood"):
82+
with pytest.raises(TypeError, match='data type "foo" not understood'):
8383
parser.read_csv(StringIO(data), dtype={"one": "foo", 1: "int"})
8484

8585

0 commit comments

Comments
 (0)