diff --git a/doc/source/whatsnew/v0.20.0.txt b/doc/source/whatsnew/v0.20.0.txt index dc06fbd159457..d42e8edc6dfe0 100644 --- a/doc/source/whatsnew/v0.20.0.txt +++ b/doc/source/whatsnew/v0.20.0.txt @@ -253,7 +253,7 @@ Bug Fixes - +- Bug in ``Series`` construction with a datetimetz (:issue:`14928`) diff --git a/pandas/core/ops.py b/pandas/core/ops.py index 80de3cd85d4db..396b0e048bc49 100644 --- a/pandas/core/ops.py +++ b/pandas/core/ops.py @@ -545,9 +545,9 @@ def _offset(lvalues, rvalues): # with tz, convert to UTC if self.is_datetime64tz_lhs: - lvalues = lvalues.tz_localize(None) + lvalues = lvalues.tz_convert('UTC').tz_localize(None) if self.is_datetime64tz_rhs: - rvalues = rvalues.tz_localize(None) + rvalues = rvalues.tz_convert('UTC').tz_localize(None) lvalues = lvalues.view(np.int64) rvalues = rvalues.view(np.int64) diff --git a/pandas/tests/series/test_constructors.py b/pandas/tests/series/test_constructors.py index ed7b0fda19cb7..a7e3ebdfc43d0 100644 --- a/pandas/tests/series/test_constructors.py +++ b/pandas/tests/series/test_constructors.py @@ -529,6 +529,21 @@ def test_constructor_with_datetime_tz(self): expected = Series(pd.DatetimeIndex(['NaT', 'NaT'], tz='US/Eastern')) assert_series_equal(s, expected) + def test_construction_consistency(self): + + # make sure that we are not re-localizing upon construction + # GH 14928 + s = Series(pd.date_range('20130101', periods=3, tz='US/Eastern')) + + result = Series(s, dtype=s.dtype) + tm.assert_series_equal(result, s) + + result = Series(s.dt.tz_convert('UTC'), dtype=s.dtype) + tm.assert_series_equal(result, s) + + result = Series(s.values, dtype=s.dtype) + tm.assert_series_equal(result, s) + def test_constructor_periodindex(self): # GH7932 # converting a PeriodIndex when put in a Series diff --git a/pandas/types/cast.py b/pandas/types/cast.py index 4f4f95d5a455b..ff4fb73d6a9b6 100644 --- a/pandas/types/cast.py +++ b/pandas/types/cast.py @@ -823,9 +823,10 @@ def _possibly_cast_to_datetime(value, dtype, errors='raise'): elif is_datetime64tz: # input has to be UTC at this point, so just # localize - value = to_datetime( - value, - errors=errors).tz_localize(dtype.tz) + value = (to_datetime(value, errors=errors) + .tz_localize('UTC') + .tz_convert(dtype.tz) + ) elif is_timedelta64: value = to_timedelta(value, errors=errors)._values except (AttributeError, ValueError, TypeError):