init
This commit is contained in:
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
+176
@@ -0,0 +1,176 @@
|
||||
from datetime import timedelta
|
||||
|
||||
import numpy as np
|
||||
import pytest
|
||||
|
||||
import pandas as pd
|
||||
from pandas import (
|
||||
Index,
|
||||
NaT,
|
||||
Timedelta,
|
||||
TimedeltaIndex,
|
||||
timedelta_range,
|
||||
)
|
||||
import pandas._testing as tm
|
||||
from pandas.core.arrays import TimedeltaArray
|
||||
|
||||
|
||||
class TestTimedeltaIndex:
|
||||
def test_astype_object(self):
|
||||
idx = timedelta_range(start="1 days", periods=4, freq="D", name="idx")
|
||||
expected_list = [
|
||||
Timedelta("1 days"),
|
||||
Timedelta("2 days"),
|
||||
Timedelta("3 days"),
|
||||
Timedelta("4 days"),
|
||||
]
|
||||
result = idx.astype(object)
|
||||
expected = Index(expected_list, dtype=object, name="idx")
|
||||
tm.assert_index_equal(result, expected)
|
||||
assert idx.tolist() == expected_list
|
||||
|
||||
def test_astype_object_with_nat(self):
|
||||
idx = TimedeltaIndex(
|
||||
[timedelta(days=1), timedelta(days=2), NaT, timedelta(days=4)], name="idx"
|
||||
)
|
||||
expected_list = [
|
||||
Timedelta("1 days"),
|
||||
Timedelta("2 days"),
|
||||
NaT,
|
||||
Timedelta("4 days"),
|
||||
]
|
||||
result = idx.astype(object)
|
||||
expected = Index(expected_list, dtype=object, name="idx")
|
||||
tm.assert_index_equal(result, expected)
|
||||
assert idx.tolist() == expected_list
|
||||
|
||||
def test_astype(self):
|
||||
# GH 13149, GH 13209
|
||||
idx = TimedeltaIndex([1e14, "NaT", NaT, np.nan], name="idx")
|
||||
|
||||
result = idx.astype(object)
|
||||
expected = Index(
|
||||
[Timedelta("1 days 03:46:40")] + [NaT] * 3, dtype=object, name="idx"
|
||||
)
|
||||
tm.assert_index_equal(result, expected)
|
||||
|
||||
result = idx.astype(np.int64)
|
||||
expected = Index(
|
||||
[100000000000000] + [-9223372036854775808] * 3, dtype=np.int64, name="idx"
|
||||
)
|
||||
tm.assert_index_equal(result, expected)
|
||||
|
||||
result = idx.astype(str)
|
||||
expected = Index([str(x) for x in idx], name="idx", dtype=object)
|
||||
tm.assert_index_equal(result, expected)
|
||||
|
||||
rng = timedelta_range("1 days", periods=10)
|
||||
result = rng.astype("i8")
|
||||
tm.assert_index_equal(result, Index(rng.asi8))
|
||||
tm.assert_numpy_array_equal(rng.asi8, result.values)
|
||||
|
||||
def test_astype_uint(self):
|
||||
arr = timedelta_range("1h", periods=2)
|
||||
|
||||
with pytest.raises(TypeError, match=r"Do obj.astype\('int64'\)"):
|
||||
arr.astype("uint64")
|
||||
with pytest.raises(TypeError, match=r"Do obj.astype\('int64'\)"):
|
||||
arr.astype("uint32")
|
||||
|
||||
def test_astype_timedelta64(self):
|
||||
# GH 13149, GH 13209
|
||||
idx = TimedeltaIndex([1e14, "NaT", NaT, np.nan])
|
||||
|
||||
msg = (
|
||||
r"Cannot convert from timedelta64\[ns\] to timedelta64. "
|
||||
"Supported resolutions are 's', 'ms', 'us', 'ns'"
|
||||
)
|
||||
with pytest.raises(ValueError, match=msg):
|
||||
idx.astype("timedelta64")
|
||||
|
||||
result = idx.astype("timedelta64[ns]")
|
||||
tm.assert_index_equal(result, idx)
|
||||
assert result is not idx
|
||||
|
||||
result = idx.astype("timedelta64[ns]", copy=False)
|
||||
tm.assert_index_equal(result, idx)
|
||||
assert result is idx
|
||||
|
||||
def test_astype_to_td64d_raises(self, index_or_series):
|
||||
# We don't support "D" reso
|
||||
scalar = Timedelta(days=31)
|
||||
td = index_or_series(
|
||||
[scalar, scalar, scalar + timedelta(minutes=5, seconds=3), NaT],
|
||||
dtype="m8[ns]",
|
||||
)
|
||||
msg = (
|
||||
r"Cannot convert from timedelta64\[ns\] to timedelta64\[D\]. "
|
||||
"Supported resolutions are 's', 'ms', 'us', 'ns'"
|
||||
)
|
||||
with pytest.raises(ValueError, match=msg):
|
||||
td.astype("timedelta64[D]")
|
||||
|
||||
def test_astype_ms_to_s(self, index_or_series):
|
||||
scalar = Timedelta(days=31)
|
||||
td = index_or_series(
|
||||
[scalar, scalar, scalar + timedelta(minutes=5, seconds=3), NaT],
|
||||
dtype="m8[ns]",
|
||||
)
|
||||
|
||||
exp_values = np.asarray(td).astype("m8[s]")
|
||||
exp_tda = TimedeltaArray._simple_new(exp_values, dtype=exp_values.dtype)
|
||||
expected = index_or_series(exp_tda)
|
||||
assert expected.dtype == "m8[s]"
|
||||
result = td.astype("timedelta64[s]")
|
||||
tm.assert_equal(result, expected)
|
||||
|
||||
def test_astype_freq_conversion(self):
|
||||
# pre-2.0 td64 astype converted to float64. now for supported units
|
||||
# (s, ms, us, ns) this converts to the requested dtype.
|
||||
# This matches TDA and Series
|
||||
tdi = timedelta_range("1 Day", periods=30)
|
||||
|
||||
res = tdi.astype("m8[s]")
|
||||
exp_values = np.asarray(tdi).astype("m8[s]")
|
||||
exp_tda = TimedeltaArray._simple_new(
|
||||
exp_values, dtype=exp_values.dtype, freq=tdi.freq
|
||||
)
|
||||
expected = Index(exp_tda)
|
||||
assert expected.dtype == "m8[s]"
|
||||
tm.assert_index_equal(res, expected)
|
||||
|
||||
# check this matches Series and TimedeltaArray
|
||||
res = tdi._data.astype("m8[s]")
|
||||
tm.assert_equal(res, expected._values)
|
||||
|
||||
res = tdi.to_series().astype("m8[s]")
|
||||
tm.assert_equal(res._values, expected._values._with_freq(None))
|
||||
|
||||
@pytest.mark.parametrize("dtype", [float, "datetime64", "datetime64[ns]"])
|
||||
def test_astype_raises(self, dtype):
|
||||
# GH 13149, GH 13209
|
||||
idx = TimedeltaIndex([1e14, "NaT", NaT, np.nan])
|
||||
msg = "Cannot cast TimedeltaIndex to dtype"
|
||||
with pytest.raises(TypeError, match=msg):
|
||||
idx.astype(dtype)
|
||||
|
||||
def test_astype_category(self):
|
||||
obj = timedelta_range("1h", periods=2, freq="h")
|
||||
|
||||
result = obj.astype("category")
|
||||
expected = pd.CategoricalIndex([Timedelta("1h"), Timedelta("2h")])
|
||||
tm.assert_index_equal(result, expected)
|
||||
|
||||
result = obj._data.astype("category")
|
||||
expected = expected.values
|
||||
tm.assert_categorical_equal(result, expected)
|
||||
|
||||
def test_astype_array_fallback(self):
|
||||
obj = timedelta_range("1h", periods=2)
|
||||
result = obj.astype(bool)
|
||||
expected = Index(np.array([True, True]))
|
||||
tm.assert_index_equal(result, expected)
|
||||
|
||||
result = obj._data.astype(bool)
|
||||
expected = np.array([True, True])
|
||||
tm.assert_numpy_array_equal(result, expected)
|
||||
+40
@@ -0,0 +1,40 @@
|
||||
import numpy as np
|
||||
|
||||
from pandas import (
|
||||
TimedeltaIndex,
|
||||
factorize,
|
||||
timedelta_range,
|
||||
)
|
||||
import pandas._testing as tm
|
||||
|
||||
|
||||
class TestTimedeltaIndexFactorize:
|
||||
def test_factorize(self):
|
||||
idx1 = TimedeltaIndex(["1 day", "1 day", "2 day", "2 day", "3 day", "3 day"])
|
||||
|
||||
exp_arr = np.array([0, 0, 1, 1, 2, 2], dtype=np.intp)
|
||||
exp_idx = TimedeltaIndex(["1 day", "2 day", "3 day"])
|
||||
|
||||
arr, idx = idx1.factorize()
|
||||
tm.assert_numpy_array_equal(arr, exp_arr)
|
||||
tm.assert_index_equal(idx, exp_idx)
|
||||
assert idx.freq == exp_idx.freq
|
||||
|
||||
arr, idx = idx1.factorize(sort=True)
|
||||
tm.assert_numpy_array_equal(arr, exp_arr)
|
||||
tm.assert_index_equal(idx, exp_idx)
|
||||
assert idx.freq == exp_idx.freq
|
||||
|
||||
def test_factorize_preserves_freq(self):
|
||||
# GH#38120 freq should be preserved
|
||||
idx3 = timedelta_range("1 day", periods=4, freq="s")
|
||||
exp_arr = np.array([0, 1, 2, 3], dtype=np.intp)
|
||||
arr, idx = idx3.factorize()
|
||||
tm.assert_numpy_array_equal(arr, exp_arr)
|
||||
tm.assert_index_equal(idx, idx3)
|
||||
assert idx.freq == idx3.freq
|
||||
|
||||
arr, idx = factorize(idx3)
|
||||
tm.assert_numpy_array_equal(arr, exp_arr)
|
||||
tm.assert_index_equal(idx, idx3)
|
||||
assert idx.freq == idx3.freq
|
||||
+22
@@ -0,0 +1,22 @@
|
||||
from pandas import (
|
||||
Index,
|
||||
NaT,
|
||||
Timedelta,
|
||||
TimedeltaIndex,
|
||||
)
|
||||
import pandas._testing as tm
|
||||
|
||||
|
||||
class TestFillNA:
|
||||
def test_fillna_timedelta(self):
|
||||
# GH#11343
|
||||
idx = TimedeltaIndex(["1 day", NaT, "3 day"])
|
||||
|
||||
exp = TimedeltaIndex(["1 day", "2 day", "3 day"])
|
||||
tm.assert_index_equal(idx.fillna(Timedelta("2 day")), exp)
|
||||
|
||||
exp = TimedeltaIndex(["1 day", "3 hour", "3 day"])
|
||||
idx.fillna(Timedelta("3 hour"))
|
||||
|
||||
exp = Index([Timedelta("1 day"), "x", Timedelta("3 day")], dtype=object)
|
||||
tm.assert_index_equal(idx.fillna("x"), exp)
|
||||
+145
@@ -0,0 +1,145 @@
|
||||
from datetime import timedelta
|
||||
|
||||
import numpy as np
|
||||
import pytest
|
||||
|
||||
from pandas._libs import lib
|
||||
|
||||
import pandas as pd
|
||||
from pandas import (
|
||||
Index,
|
||||
Timedelta,
|
||||
TimedeltaIndex,
|
||||
timedelta_range,
|
||||
)
|
||||
import pandas._testing as tm
|
||||
|
||||
|
||||
class TestTimedeltaIndexInsert:
|
||||
def test_insert(self):
|
||||
idx = TimedeltaIndex(["4day", "1day", "2day"], name="idx")
|
||||
|
||||
result = idx.insert(2, timedelta(days=5))
|
||||
exp = TimedeltaIndex(["4day", "1day", "5day", "2day"], name="idx")
|
||||
tm.assert_index_equal(result, exp)
|
||||
|
||||
# insertion of non-datetime should coerce to object index
|
||||
result = idx.insert(1, "inserted")
|
||||
expected = Index(
|
||||
[Timedelta("4day"), "inserted", Timedelta("1day"), Timedelta("2day")],
|
||||
name="idx",
|
||||
)
|
||||
assert not isinstance(result, TimedeltaIndex)
|
||||
tm.assert_index_equal(result, expected)
|
||||
assert result.name == expected.name
|
||||
|
||||
idx = timedelta_range("1day 00:00:01", periods=3, freq="s", name="idx")
|
||||
|
||||
# preserve freq
|
||||
expected_0 = TimedeltaIndex(
|
||||
["1day", "1day 00:00:01", "1day 00:00:02", "1day 00:00:03"],
|
||||
name="idx",
|
||||
freq="s",
|
||||
)
|
||||
expected_3 = TimedeltaIndex(
|
||||
["1day 00:00:01", "1day 00:00:02", "1day 00:00:03", "1day 00:00:04"],
|
||||
name="idx",
|
||||
freq="s",
|
||||
)
|
||||
|
||||
# reset freq to None
|
||||
expected_1_nofreq = TimedeltaIndex(
|
||||
["1day 00:00:01", "1day 00:00:01", "1day 00:00:02", "1day 00:00:03"],
|
||||
name="idx",
|
||||
freq=None,
|
||||
)
|
||||
expected_3_nofreq = TimedeltaIndex(
|
||||
["1day 00:00:01", "1day 00:00:02", "1day 00:00:03", "1day 00:00:05"],
|
||||
name="idx",
|
||||
freq=None,
|
||||
)
|
||||
|
||||
cases = [
|
||||
(0, Timedelta("1day"), expected_0),
|
||||
(-3, Timedelta("1day"), expected_0),
|
||||
(3, Timedelta("1day 00:00:04"), expected_3),
|
||||
(1, Timedelta("1day 00:00:01"), expected_1_nofreq),
|
||||
(3, Timedelta("1day 00:00:05"), expected_3_nofreq),
|
||||
]
|
||||
|
||||
for n, d, expected in cases:
|
||||
result = idx.insert(n, d)
|
||||
tm.assert_index_equal(result, expected)
|
||||
assert result.name == expected.name
|
||||
assert result.freq == expected.freq
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
"null", [None, np.nan, np.timedelta64("NaT"), pd.NaT, pd.NA]
|
||||
)
|
||||
def test_insert_nat(self, null):
|
||||
# GH 18295 (test missing)
|
||||
idx = timedelta_range("1day", "3day")
|
||||
result = idx.insert(1, null)
|
||||
expected = TimedeltaIndex(["1day", pd.NaT, "2day", "3day"])
|
||||
tm.assert_index_equal(result, expected)
|
||||
|
||||
def test_insert_invalid_na(self):
|
||||
idx = TimedeltaIndex(["4day", "1day", "2day"], name="idx")
|
||||
|
||||
item = np.datetime64("NaT")
|
||||
result = idx.insert(0, item)
|
||||
|
||||
expected = Index([item] + list(idx), dtype=object, name="idx")
|
||||
tm.assert_index_equal(result, expected)
|
||||
|
||||
# Also works if we pass a different dt64nat object
|
||||
item2 = np.datetime64("NaT")
|
||||
result = idx.insert(0, item2)
|
||||
tm.assert_index_equal(result, expected)
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
"item", [0, np.int64(0), np.float64(0), np.array(0), np.datetime64(456, "us")]
|
||||
)
|
||||
def test_insert_mismatched_types_raises(self, item):
|
||||
# GH#33703 dont cast these to td64
|
||||
tdi = TimedeltaIndex(["4day", "1day", "2day"], name="idx")
|
||||
|
||||
result = tdi.insert(1, item)
|
||||
|
||||
expected = Index(
|
||||
[tdi[0], lib.item_from_zerodim(item)] + list(tdi[1:]),
|
||||
dtype=object,
|
||||
name="idx",
|
||||
)
|
||||
tm.assert_index_equal(result, expected)
|
||||
|
||||
def test_insert_castable_str(self):
|
||||
idx = timedelta_range("1day", "3day")
|
||||
|
||||
result = idx.insert(0, "1 Day")
|
||||
|
||||
expected = TimedeltaIndex([idx[0]] + list(idx))
|
||||
tm.assert_index_equal(result, expected)
|
||||
|
||||
def test_insert_non_castable_str(self):
|
||||
idx = timedelta_range("1day", "3day")
|
||||
|
||||
result = idx.insert(0, "foo")
|
||||
|
||||
expected = Index(["foo"] + list(idx), dtype=object)
|
||||
tm.assert_index_equal(result, expected)
|
||||
|
||||
def test_insert_empty(self):
|
||||
# Corner case inserting with length zero doesn't raise IndexError
|
||||
# GH#33573 for freq preservation
|
||||
idx = timedelta_range("1 Day", periods=3)
|
||||
td = idx[0]
|
||||
|
||||
result = idx[:0].insert(0, td)
|
||||
assert result.freq == "D"
|
||||
|
||||
with pytest.raises(IndexError, match="loc must be an integer between"):
|
||||
result = idx[:0].insert(1, td)
|
||||
|
||||
with pytest.raises(IndexError, match="loc must be an integer between"):
|
||||
result = idx[:0].insert(-1, td)
|
||||
+34
@@ -0,0 +1,34 @@
|
||||
import numpy as np
|
||||
|
||||
from pandas import (
|
||||
TimedeltaIndex,
|
||||
timedelta_range,
|
||||
)
|
||||
import pandas._testing as tm
|
||||
|
||||
|
||||
class TestRepeat:
|
||||
def test_repeat(self):
|
||||
index = timedelta_range("1 days", periods=2, freq="D")
|
||||
exp = TimedeltaIndex(["1 days", "1 days", "2 days", "2 days"])
|
||||
for res in [index.repeat(2), np.repeat(index, 2)]:
|
||||
tm.assert_index_equal(res, exp)
|
||||
assert res.freq is None
|
||||
|
||||
index = TimedeltaIndex(["1 days", "NaT", "3 days"])
|
||||
exp = TimedeltaIndex(
|
||||
[
|
||||
"1 days",
|
||||
"1 days",
|
||||
"1 days",
|
||||
"NaT",
|
||||
"NaT",
|
||||
"NaT",
|
||||
"3 days",
|
||||
"3 days",
|
||||
"3 days",
|
||||
]
|
||||
)
|
||||
for res in [index.repeat(3), np.repeat(index, 3)]:
|
||||
tm.assert_index_equal(res, exp)
|
||||
assert res.freq is None
|
||||
+76
@@ -0,0 +1,76 @@
|
||||
import pytest
|
||||
|
||||
from pandas.errors import NullFrequencyError
|
||||
|
||||
import pandas as pd
|
||||
from pandas import TimedeltaIndex
|
||||
import pandas._testing as tm
|
||||
|
||||
|
||||
class TestTimedeltaIndexShift:
|
||||
# -------------------------------------------------------------
|
||||
# TimedeltaIndex.shift is used by __add__/__sub__
|
||||
|
||||
def test_tdi_shift_empty(self):
|
||||
# GH#9903
|
||||
idx = TimedeltaIndex([], name="xxx")
|
||||
tm.assert_index_equal(idx.shift(0, freq="h"), idx)
|
||||
tm.assert_index_equal(idx.shift(3, freq="h"), idx)
|
||||
|
||||
def test_tdi_shift_hours(self):
|
||||
# GH#9903
|
||||
idx = TimedeltaIndex(["5 hours", "6 hours", "9 hours"], name="xxx")
|
||||
tm.assert_index_equal(idx.shift(0, freq="h"), idx)
|
||||
exp = TimedeltaIndex(["8 hours", "9 hours", "12 hours"], name="xxx")
|
||||
tm.assert_index_equal(idx.shift(3, freq="h"), exp)
|
||||
exp = TimedeltaIndex(["2 hours", "3 hours", "6 hours"], name="xxx")
|
||||
tm.assert_index_equal(idx.shift(-3, freq="h"), exp)
|
||||
|
||||
def test_tdi_shift_minutes(self):
|
||||
# GH#9903
|
||||
idx = TimedeltaIndex(["5 hours", "6 hours", "9 hours"], name="xxx")
|
||||
tm.assert_index_equal(idx.shift(0, freq="min"), idx)
|
||||
exp = TimedeltaIndex(["05:03:00", "06:03:00", "9:03:00"], name="xxx")
|
||||
tm.assert_index_equal(idx.shift(3, freq="min"), exp)
|
||||
exp = TimedeltaIndex(["04:57:00", "05:57:00", "8:57:00"], name="xxx")
|
||||
tm.assert_index_equal(idx.shift(-3, freq="min"), exp)
|
||||
|
||||
def test_tdi_shift_int(self):
|
||||
# GH#8083
|
||||
tdi = pd.to_timedelta(range(5), unit="d")
|
||||
trange = tdi._with_freq("infer") + pd.offsets.Hour(1)
|
||||
result = trange.shift(1)
|
||||
expected = TimedeltaIndex(
|
||||
[
|
||||
"1 days 01:00:00",
|
||||
"2 days 01:00:00",
|
||||
"3 days 01:00:00",
|
||||
"4 days 01:00:00",
|
||||
"5 days 01:00:00",
|
||||
],
|
||||
freq="D",
|
||||
)
|
||||
tm.assert_index_equal(result, expected)
|
||||
|
||||
def test_tdi_shift_nonstandard_freq(self):
|
||||
# GH#8083
|
||||
tdi = pd.to_timedelta(range(5), unit="d")
|
||||
trange = tdi._with_freq("infer") + pd.offsets.Hour(1)
|
||||
result = trange.shift(3, freq="2D 1s")
|
||||
expected = TimedeltaIndex(
|
||||
[
|
||||
"6 days 01:00:03",
|
||||
"7 days 01:00:03",
|
||||
"8 days 01:00:03",
|
||||
"9 days 01:00:03",
|
||||
"10 days 01:00:03",
|
||||
],
|
||||
freq="D",
|
||||
)
|
||||
tm.assert_index_equal(result, expected)
|
||||
|
||||
def test_shift_no_freq(self):
|
||||
# GH#19147
|
||||
tdi = TimedeltaIndex(["1 days 01:00:00", "2 days 01:00:00"], freq=None)
|
||||
with pytest.raises(NullFrequencyError, match="Cannot shift with no freq"):
|
||||
tdi.shift(2)
|
||||
Reference in New Issue
Block a user