1450 lines
50 KiB
Python
1450 lines
50 KiB
Python
|
import pytest
|
||
|
|
||
|
import pytz
|
||
|
import numpy as np
|
||
|
from datetime import datetime, date, timedelta
|
||
|
|
||
|
import pandas as pd
|
||
|
import pandas.util.testing as tm
|
||
|
import pandas.core.indexes.period as period
|
||
|
from pandas.compat import text_type, iteritems
|
||
|
from pandas.compat.numpy import np_datetime64_compat
|
||
|
|
||
|
from pandas._libs import tslib
|
||
|
from pandas._libs.tslibs import period as libperiod
|
||
|
from pandas._libs.tslibs.ccalendar import DAYS, MONTHS
|
||
|
from pandas._libs.tslibs.parsing import DateParseError
|
||
|
from pandas import Period, Timestamp, offsets
|
||
|
|
||
|
|
||
|
class TestPeriodProperties(object):
|
||
|
"Test properties such as year, month, weekday, etc...."
|
||
|
|
||
|
@pytest.mark.parametrize('freq', ['A', 'M', 'D', 'H'])
|
||
|
def test_is_leap_year(self, freq):
|
||
|
# GH 13727
|
||
|
p = Period('2000-01-01 00:00:00', freq=freq)
|
||
|
assert p.is_leap_year
|
||
|
assert isinstance(p.is_leap_year, bool)
|
||
|
|
||
|
p = Period('1999-01-01 00:00:00', freq=freq)
|
||
|
assert not p.is_leap_year
|
||
|
|
||
|
p = Period('2004-01-01 00:00:00', freq=freq)
|
||
|
assert p.is_leap_year
|
||
|
|
||
|
p = Period('2100-01-01 00:00:00', freq=freq)
|
||
|
assert not p.is_leap_year
|
||
|
|
||
|
def test_quarterly_negative_ordinals(self):
|
||
|
p = Period(ordinal=-1, freq='Q-DEC')
|
||
|
assert p.year == 1969
|
||
|
assert p.quarter == 4
|
||
|
assert isinstance(p, Period)
|
||
|
|
||
|
p = Period(ordinal=-2, freq='Q-DEC')
|
||
|
assert p.year == 1969
|
||
|
assert p.quarter == 3
|
||
|
assert isinstance(p, Period)
|
||
|
|
||
|
p = Period(ordinal=-2, freq='M')
|
||
|
assert p.year == 1969
|
||
|
assert p.month == 11
|
||
|
assert isinstance(p, Period)
|
||
|
|
||
|
@pytest.mark.parametrize('month', MONTHS)
|
||
|
def test_period_cons_quarterly(self, month):
|
||
|
# bugs in scikits.timeseries
|
||
|
freq = 'Q-%s' % month
|
||
|
exp = Period('1989Q3', freq=freq)
|
||
|
assert '1989Q3' in str(exp)
|
||
|
stamp = exp.to_timestamp('D', how='end')
|
||
|
p = Period(stamp, freq=freq)
|
||
|
assert p == exp
|
||
|
|
||
|
stamp = exp.to_timestamp('3D', how='end')
|
||
|
p = Period(stamp, freq=freq)
|
||
|
assert p == exp
|
||
|
|
||
|
@pytest.mark.parametrize('month', MONTHS)
|
||
|
def test_period_cons_annual(self, month):
|
||
|
# bugs in scikits.timeseries
|
||
|
freq = 'A-%s' % month
|
||
|
exp = Period('1989', freq=freq)
|
||
|
stamp = exp.to_timestamp('D', how='end') + timedelta(days=30)
|
||
|
p = Period(stamp, freq=freq)
|
||
|
assert p == exp + 1
|
||
|
assert isinstance(p, Period)
|
||
|
|
||
|
@pytest.mark.parametrize('day', DAYS)
|
||
|
@pytest.mark.parametrize('num', range(10, 17))
|
||
|
def test_period_cons_weekly(self, num, day):
|
||
|
daystr = '2011-02-%d' % num
|
||
|
freq = 'W-%s' % day
|
||
|
|
||
|
result = Period(daystr, freq=freq)
|
||
|
expected = Period(daystr, freq='D').asfreq(freq)
|
||
|
assert result == expected
|
||
|
assert isinstance(result, Period)
|
||
|
|
||
|
def test_period_from_ordinal(self):
|
||
|
p = pd.Period('2011-01', freq='M')
|
||
|
res = pd.Period._from_ordinal(p.ordinal, freq='M')
|
||
|
assert p == res
|
||
|
assert isinstance(res, Period)
|
||
|
|
||
|
def test_period_cons_nat(self):
|
||
|
p = Period('NaT', freq='M')
|
||
|
assert p is pd.NaT
|
||
|
|
||
|
p = Period('nat', freq='W-SUN')
|
||
|
assert p is pd.NaT
|
||
|
|
||
|
p = Period(tslib.iNaT, freq='D')
|
||
|
assert p is pd.NaT
|
||
|
|
||
|
p = Period(tslib.iNaT, freq='3D')
|
||
|
assert p is pd.NaT
|
||
|
|
||
|
p = Period(tslib.iNaT, freq='1D1H')
|
||
|
assert p is pd.NaT
|
||
|
|
||
|
p = Period('NaT')
|
||
|
assert p is pd.NaT
|
||
|
|
||
|
p = Period(tslib.iNaT)
|
||
|
assert p is pd.NaT
|
||
|
|
||
|
def test_period_cons_mult(self):
|
||
|
p1 = Period('2011-01', freq='3M')
|
||
|
p2 = Period('2011-01', freq='M')
|
||
|
assert p1.ordinal == p2.ordinal
|
||
|
|
||
|
assert p1.freq == offsets.MonthEnd(3)
|
||
|
assert p1.freqstr == '3M'
|
||
|
|
||
|
assert p2.freq == offsets.MonthEnd()
|
||
|
assert p2.freqstr == 'M'
|
||
|
|
||
|
result = p1 + 1
|
||
|
assert result.ordinal == (p2 + 3).ordinal
|
||
|
assert result.freq == p1.freq
|
||
|
assert result.freqstr == '3M'
|
||
|
|
||
|
result = p1 - 1
|
||
|
assert result.ordinal == (p2 - 3).ordinal
|
||
|
assert result.freq == p1.freq
|
||
|
assert result.freqstr == '3M'
|
||
|
|
||
|
msg = ('Frequency must be positive, because it'
|
||
|
' represents span: -3M')
|
||
|
with tm.assert_raises_regex(ValueError, msg):
|
||
|
Period('2011-01', freq='-3M')
|
||
|
|
||
|
msg = ('Frequency must be positive, because it' ' represents span: 0M')
|
||
|
with tm.assert_raises_regex(ValueError, msg):
|
||
|
Period('2011-01', freq='0M')
|
||
|
|
||
|
def test_period_cons_combined(self):
|
||
|
p = [(Period('2011-01', freq='1D1H'),
|
||
|
Period('2011-01', freq='1H1D'),
|
||
|
Period('2011-01', freq='H')),
|
||
|
(Period(ordinal=1, freq='1D1H'),
|
||
|
Period(ordinal=1, freq='1H1D'),
|
||
|
Period(ordinal=1, freq='H'))]
|
||
|
|
||
|
for p1, p2, p3 in p:
|
||
|
assert p1.ordinal == p3.ordinal
|
||
|
assert p2.ordinal == p3.ordinal
|
||
|
|
||
|
assert p1.freq == offsets.Hour(25)
|
||
|
assert p1.freqstr == '25H'
|
||
|
|
||
|
assert p2.freq == offsets.Hour(25)
|
||
|
assert p2.freqstr == '25H'
|
||
|
|
||
|
assert p3.freq == offsets.Hour()
|
||
|
assert p3.freqstr == 'H'
|
||
|
|
||
|
result = p1 + 1
|
||
|
assert result.ordinal == (p3 + 25).ordinal
|
||
|
assert result.freq == p1.freq
|
||
|
assert result.freqstr == '25H'
|
||
|
|
||
|
result = p2 + 1
|
||
|
assert result.ordinal == (p3 + 25).ordinal
|
||
|
assert result.freq == p2.freq
|
||
|
assert result.freqstr == '25H'
|
||
|
|
||
|
result = p1 - 1
|
||
|
assert result.ordinal == (p3 - 25).ordinal
|
||
|
assert result.freq == p1.freq
|
||
|
assert result.freqstr == '25H'
|
||
|
|
||
|
result = p2 - 1
|
||
|
assert result.ordinal == (p3 - 25).ordinal
|
||
|
assert result.freq == p2.freq
|
||
|
assert result.freqstr == '25H'
|
||
|
|
||
|
msg = ('Frequency must be positive, because it'
|
||
|
' represents span: -25H')
|
||
|
with tm.assert_raises_regex(ValueError, msg):
|
||
|
Period('2011-01', freq='-1D1H')
|
||
|
with tm.assert_raises_regex(ValueError, msg):
|
||
|
Period('2011-01', freq='-1H1D')
|
||
|
with tm.assert_raises_regex(ValueError, msg):
|
||
|
Period(ordinal=1, freq='-1D1H')
|
||
|
with tm.assert_raises_regex(ValueError, msg):
|
||
|
Period(ordinal=1, freq='-1H1D')
|
||
|
|
||
|
msg = ('Frequency must be positive, because it'
|
||
|
' represents span: 0D')
|
||
|
with tm.assert_raises_regex(ValueError, msg):
|
||
|
Period('2011-01', freq='0D0H')
|
||
|
with tm.assert_raises_regex(ValueError, msg):
|
||
|
Period(ordinal=1, freq='0D0H')
|
||
|
|
||
|
# You can only combine together day and intraday offsets
|
||
|
msg = ('Invalid frequency: 1W1D')
|
||
|
with tm.assert_raises_regex(ValueError, msg):
|
||
|
Period('2011-01', freq='1W1D')
|
||
|
msg = ('Invalid frequency: 1D1W')
|
||
|
with tm.assert_raises_regex(ValueError, msg):
|
||
|
Period('2011-01', freq='1D1W')
|
||
|
|
||
|
@pytest.mark.parametrize('tzstr', ['Europe/Brussels',
|
||
|
'Asia/Tokyo', 'US/Pacific'])
|
||
|
def test_timestamp_tz_arg(self, tzstr):
|
||
|
p = Period('1/1/2005', freq='M').to_timestamp(tz=tzstr)
|
||
|
exp = Timestamp('1/1/2005', tz='UTC').tz_convert(tzstr)
|
||
|
exp_zone = pytz.timezone(tzstr).normalize(p)
|
||
|
|
||
|
assert p == exp
|
||
|
assert p.tz == exp_zone.tzinfo
|
||
|
assert p.tz == exp.tz
|
||
|
|
||
|
p = Period('1/1/2005', freq='3H').to_timestamp(tz=tzstr)
|
||
|
exp = Timestamp('1/1/2005', tz='UTC').tz_convert(tzstr)
|
||
|
exp_zone = pytz.timezone(tzstr).normalize(p)
|
||
|
|
||
|
assert p == exp
|
||
|
assert p.tz == exp_zone.tzinfo
|
||
|
assert p.tz == exp.tz
|
||
|
|
||
|
p = Period('1/1/2005', freq='A').to_timestamp(freq='A', tz=tzstr)
|
||
|
exp = Timestamp('31/12/2005', tz='UTC').tz_convert(tzstr)
|
||
|
exp_zone = pytz.timezone(tzstr).normalize(p)
|
||
|
|
||
|
assert p == exp
|
||
|
assert p.tz == exp_zone.tzinfo
|
||
|
assert p.tz == exp.tz
|
||
|
|
||
|
p = Period('1/1/2005', freq='A').to_timestamp(freq='3H', tz=tzstr)
|
||
|
exp = Timestamp('1/1/2005', tz='UTC').tz_convert(tzstr)
|
||
|
exp_zone = pytz.timezone(tzstr).normalize(p)
|
||
|
|
||
|
assert p == exp
|
||
|
assert p.tz == exp_zone.tzinfo
|
||
|
assert p.tz == exp.tz
|
||
|
|
||
|
@pytest.mark.parametrize('tzstr', ['dateutil/Europe/Brussels',
|
||
|
'dateutil/Asia/Tokyo',
|
||
|
'dateutil/US/Pacific'])
|
||
|
def test_timestamp_tz_arg_dateutil(self, tzstr):
|
||
|
from pandas._libs.tslibs.timezones import dateutil_gettz
|
||
|
from pandas._libs.tslibs.timezones import maybe_get_tz
|
||
|
tz = maybe_get_tz(tzstr)
|
||
|
p = Period('1/1/2005', freq='M').to_timestamp(tz=tz)
|
||
|
exp = Timestamp('1/1/2005', tz='UTC').tz_convert(tzstr)
|
||
|
assert p == exp
|
||
|
assert p.tz == dateutil_gettz(tzstr.split('/', 1)[1])
|
||
|
assert p.tz == exp.tz
|
||
|
|
||
|
p = Period('1/1/2005', freq='M').to_timestamp(freq='3H', tz=tz)
|
||
|
exp = Timestamp('1/1/2005', tz='UTC').tz_convert(tzstr)
|
||
|
assert p == exp
|
||
|
assert p.tz == dateutil_gettz(tzstr.split('/', 1)[1])
|
||
|
assert p.tz == exp.tz
|
||
|
|
||
|
def test_timestamp_tz_arg_dateutil_from_string(self):
|
||
|
from pandas._libs.tslibs.timezones import dateutil_gettz
|
||
|
p = Period('1/1/2005',
|
||
|
freq='M').to_timestamp(tz='dateutil/Europe/Brussels')
|
||
|
assert p.tz == dateutil_gettz('Europe/Brussels')
|
||
|
|
||
|
def test_timestamp_mult(self):
|
||
|
p = pd.Period('2011-01', freq='M')
|
||
|
assert p.to_timestamp(how='S') == pd.Timestamp('2011-01-01')
|
||
|
assert p.to_timestamp(how='E') == pd.Timestamp('2011-01-31')
|
||
|
|
||
|
p = pd.Period('2011-01', freq='3M')
|
||
|
assert p.to_timestamp(how='S') == pd.Timestamp('2011-01-01')
|
||
|
assert p.to_timestamp(how='E') == pd.Timestamp('2011-03-31')
|
||
|
|
||
|
def test_construction(self):
|
||
|
i1 = Period('1/1/2005', freq='M')
|
||
|
i2 = Period('Jan 2005')
|
||
|
|
||
|
assert i1 == i2
|
||
|
|
||
|
i1 = Period('2005', freq='A')
|
||
|
i2 = Period('2005')
|
||
|
i3 = Period('2005', freq='a')
|
||
|
|
||
|
assert i1 == i2
|
||
|
assert i1 == i3
|
||
|
|
||
|
i4 = Period('2005', freq='M')
|
||
|
i5 = Period('2005', freq='m')
|
||
|
|
||
|
pytest.raises(ValueError, i1.__ne__, i4)
|
||
|
assert i4 == i5
|
||
|
|
||
|
i1 = Period.now('Q')
|
||
|
i2 = Period(datetime.now(), freq='Q')
|
||
|
i3 = Period.now('q')
|
||
|
|
||
|
assert i1 == i2
|
||
|
assert i1 == i3
|
||
|
|
||
|
i1 = Period('1982', freq='min')
|
||
|
i2 = Period('1982', freq='MIN')
|
||
|
assert i1 == i2
|
||
|
i2 = Period('1982', freq=('Min', 1))
|
||
|
assert i1 == i2
|
||
|
|
||
|
i1 = Period(year=2005, month=3, day=1, freq='D')
|
||
|
i2 = Period('3/1/2005', freq='D')
|
||
|
assert i1 == i2
|
||
|
|
||
|
i3 = Period(year=2005, month=3, day=1, freq='d')
|
||
|
assert i1 == i3
|
||
|
|
||
|
i1 = Period('2007-01-01 09:00:00.001')
|
||
|
expected = Period(datetime(2007, 1, 1, 9, 0, 0, 1000), freq='L')
|
||
|
assert i1 == expected
|
||
|
|
||
|
expected = Period(np_datetime64_compat(
|
||
|
'2007-01-01 09:00:00.001Z'), freq='L')
|
||
|
assert i1 == expected
|
||
|
|
||
|
i1 = Period('2007-01-01 09:00:00.00101')
|
||
|
expected = Period(datetime(2007, 1, 1, 9, 0, 0, 1010), freq='U')
|
||
|
assert i1 == expected
|
||
|
|
||
|
expected = Period(np_datetime64_compat('2007-01-01 09:00:00.00101Z'),
|
||
|
freq='U')
|
||
|
assert i1 == expected
|
||
|
|
||
|
pytest.raises(ValueError, Period, ordinal=200701)
|
||
|
|
||
|
pytest.raises(ValueError, Period, '2007-1-1', freq='X')
|
||
|
|
||
|
def test_construction_bday(self):
|
||
|
|
||
|
# Biz day construction, roll forward if non-weekday
|
||
|
i1 = Period('3/10/12', freq='B')
|
||
|
i2 = Period('3/10/12', freq='D')
|
||
|
assert i1 == i2.asfreq('B')
|
||
|
i2 = Period('3/11/12', freq='D')
|
||
|
assert i1 == i2.asfreq('B')
|
||
|
i2 = Period('3/12/12', freq='D')
|
||
|
assert i1 == i2.asfreq('B')
|
||
|
|
||
|
i3 = Period('3/10/12', freq='b')
|
||
|
assert i1 == i3
|
||
|
|
||
|
i1 = Period(year=2012, month=3, day=10, freq='B')
|
||
|
i2 = Period('3/12/12', freq='B')
|
||
|
assert i1 == i2
|
||
|
|
||
|
def test_construction_quarter(self):
|
||
|
|
||
|
i1 = Period(year=2005, quarter=1, freq='Q')
|
||
|
i2 = Period('1/1/2005', freq='Q')
|
||
|
assert i1 == i2
|
||
|
|
||
|
i1 = Period(year=2005, quarter=3, freq='Q')
|
||
|
i2 = Period('9/1/2005', freq='Q')
|
||
|
assert i1 == i2
|
||
|
|
||
|
i1 = Period('2005Q1')
|
||
|
i2 = Period(year=2005, quarter=1, freq='Q')
|
||
|
i3 = Period('2005q1')
|
||
|
assert i1 == i2
|
||
|
assert i1 == i3
|
||
|
|
||
|
i1 = Period('05Q1')
|
||
|
assert i1 == i2
|
||
|
lower = Period('05q1')
|
||
|
assert i1 == lower
|
||
|
|
||
|
i1 = Period('1Q2005')
|
||
|
assert i1 == i2
|
||
|
lower = Period('1q2005')
|
||
|
assert i1 == lower
|
||
|
|
||
|
i1 = Period('1Q05')
|
||
|
assert i1 == i2
|
||
|
lower = Period('1q05')
|
||
|
assert i1 == lower
|
||
|
|
||
|
i1 = Period('4Q1984')
|
||
|
assert i1.year == 1984
|
||
|
lower = Period('4q1984')
|
||
|
assert i1 == lower
|
||
|
|
||
|
def test_construction_month(self):
|
||
|
|
||
|
expected = Period('2007-01', freq='M')
|
||
|
i1 = Period('200701', freq='M')
|
||
|
assert i1 == expected
|
||
|
|
||
|
i1 = Period('200701', freq='M')
|
||
|
assert i1 == expected
|
||
|
|
||
|
i1 = Period(200701, freq='M')
|
||
|
assert i1 == expected
|
||
|
|
||
|
i1 = Period(ordinal=200701, freq='M')
|
||
|
assert i1.year == 18695
|
||
|
|
||
|
i1 = Period(datetime(2007, 1, 1), freq='M')
|
||
|
i2 = Period('200701', freq='M')
|
||
|
assert i1 == i2
|
||
|
|
||
|
i1 = Period(date(2007, 1, 1), freq='M')
|
||
|
i2 = Period(datetime(2007, 1, 1), freq='M')
|
||
|
i3 = Period(np.datetime64('2007-01-01'), freq='M')
|
||
|
i4 = Period(np_datetime64_compat('2007-01-01 00:00:00Z'), freq='M')
|
||
|
i5 = Period(np_datetime64_compat('2007-01-01 00:00:00.000Z'), freq='M')
|
||
|
assert i1 == i2
|
||
|
assert i1 == i3
|
||
|
assert i1 == i4
|
||
|
assert i1 == i5
|
||
|
|
||
|
def test_period_constructor_offsets(self):
|
||
|
assert (Period('1/1/2005', freq=offsets.MonthEnd()) ==
|
||
|
Period('1/1/2005', freq='M'))
|
||
|
assert (Period('2005', freq=offsets.YearEnd()) ==
|
||
|
Period('2005', freq='A'))
|
||
|
assert (Period('2005', freq=offsets.MonthEnd()) ==
|
||
|
Period('2005', freq='M'))
|
||
|
assert (Period('3/10/12', freq=offsets.BusinessDay()) ==
|
||
|
Period('3/10/12', freq='B'))
|
||
|
assert (Period('3/10/12', freq=offsets.Day()) ==
|
||
|
Period('3/10/12', freq='D'))
|
||
|
|
||
|
assert (Period(year=2005, quarter=1,
|
||
|
freq=offsets.QuarterEnd(startingMonth=12)) ==
|
||
|
Period(year=2005, quarter=1, freq='Q'))
|
||
|
assert (Period(year=2005, quarter=2,
|
||
|
freq=offsets.QuarterEnd(startingMonth=12)) ==
|
||
|
Period(year=2005, quarter=2, freq='Q'))
|
||
|
|
||
|
assert (Period(year=2005, month=3, day=1, freq=offsets.Day()) ==
|
||
|
Period(year=2005, month=3, day=1, freq='D'))
|
||
|
assert (Period(year=2012, month=3, day=10, freq=offsets.BDay()) ==
|
||
|
Period(year=2012, month=3, day=10, freq='B'))
|
||
|
|
||
|
expected = Period('2005-03-01', freq='3D')
|
||
|
assert (Period(year=2005, month=3, day=1,
|
||
|
freq=offsets.Day(3)) == expected)
|
||
|
assert Period(year=2005, month=3, day=1, freq='3D') == expected
|
||
|
|
||
|
assert (Period(year=2012, month=3, day=10,
|
||
|
freq=offsets.BDay(3)) ==
|
||
|
Period(year=2012, month=3, day=10, freq='3B'))
|
||
|
|
||
|
assert (Period(200701, freq=offsets.MonthEnd()) ==
|
||
|
Period(200701, freq='M'))
|
||
|
|
||
|
i1 = Period(ordinal=200701, freq=offsets.MonthEnd())
|
||
|
i2 = Period(ordinal=200701, freq='M')
|
||
|
assert i1 == i2
|
||
|
assert i1.year == 18695
|
||
|
assert i2.year == 18695
|
||
|
|
||
|
i1 = Period(datetime(2007, 1, 1), freq='M')
|
||
|
i2 = Period('200701', freq='M')
|
||
|
assert i1 == i2
|
||
|
|
||
|
i1 = Period(date(2007, 1, 1), freq='M')
|
||
|
i2 = Period(datetime(2007, 1, 1), freq='M')
|
||
|
i3 = Period(np.datetime64('2007-01-01'), freq='M')
|
||
|
i4 = Period(np_datetime64_compat('2007-01-01 00:00:00Z'), freq='M')
|
||
|
i5 = Period(np_datetime64_compat('2007-01-01 00:00:00.000Z'), freq='M')
|
||
|
assert i1 == i2
|
||
|
assert i1 == i3
|
||
|
assert i1 == i4
|
||
|
assert i1 == i5
|
||
|
|
||
|
i1 = Period('2007-01-01 09:00:00.001')
|
||
|
expected = Period(datetime(2007, 1, 1, 9, 0, 0, 1000), freq='L')
|
||
|
assert i1 == expected
|
||
|
|
||
|
expected = Period(np_datetime64_compat(
|
||
|
'2007-01-01 09:00:00.001Z'), freq='L')
|
||
|
assert i1 == expected
|
||
|
|
||
|
i1 = Period('2007-01-01 09:00:00.00101')
|
||
|
expected = Period(datetime(2007, 1, 1, 9, 0, 0, 1010), freq='U')
|
||
|
assert i1 == expected
|
||
|
|
||
|
expected = Period(np_datetime64_compat('2007-01-01 09:00:00.00101Z'),
|
||
|
freq='U')
|
||
|
assert i1 == expected
|
||
|
|
||
|
pytest.raises(ValueError, Period, ordinal=200701)
|
||
|
|
||
|
pytest.raises(ValueError, Period, '2007-1-1', freq='X')
|
||
|
|
||
|
def test_freq_str(self):
|
||
|
i1 = Period('1982', freq='Min')
|
||
|
assert i1.freq == offsets.Minute()
|
||
|
assert i1.freqstr == 'T'
|
||
|
|
||
|
def test_period_deprecated_freq(self):
|
||
|
cases = {"M": ["MTH", "MONTH", "MONTHLY", "Mth", "month", "monthly"],
|
||
|
"B": ["BUS", "BUSINESS", "BUSINESSLY", "WEEKDAY", "bus"],
|
||
|
"D": ["DAY", "DLY", "DAILY", "Day", "Dly", "Daily"],
|
||
|
"H": ["HR", "HOUR", "HRLY", "HOURLY", "hr", "Hour", "HRly"],
|
||
|
"T": ["minute", "MINUTE", "MINUTELY", "minutely"],
|
||
|
"S": ["sec", "SEC", "SECOND", "SECONDLY", "second"],
|
||
|
"L": ["MILLISECOND", "MILLISECONDLY", "millisecond"],
|
||
|
"U": ["MICROSECOND", "MICROSECONDLY", "microsecond"],
|
||
|
"N": ["NANOSECOND", "NANOSECONDLY", "nanosecond"]}
|
||
|
|
||
|
msg = pd._libs.tslibs.frequencies._INVALID_FREQ_ERROR
|
||
|
for exp, freqs in iteritems(cases):
|
||
|
for freq in freqs:
|
||
|
with tm.assert_raises_regex(ValueError, msg):
|
||
|
Period('2016-03-01 09:00', freq=freq)
|
||
|
with tm.assert_raises_regex(ValueError, msg):
|
||
|
Period(ordinal=1, freq=freq)
|
||
|
|
||
|
# check supported freq-aliases still works
|
||
|
p1 = Period('2016-03-01 09:00', freq=exp)
|
||
|
p2 = Period(ordinal=1, freq=exp)
|
||
|
assert isinstance(p1, Period)
|
||
|
assert isinstance(p2, Period)
|
||
|
|
||
|
def test_hash(self):
|
||
|
assert (hash(Period('2011-01', freq='M')) ==
|
||
|
hash(Period('2011-01', freq='M')))
|
||
|
|
||
|
assert (hash(Period('2011-01-01', freq='D')) !=
|
||
|
hash(Period('2011-01', freq='M')))
|
||
|
|
||
|
assert (hash(Period('2011-01', freq='3M')) !=
|
||
|
hash(Period('2011-01', freq='2M')))
|
||
|
|
||
|
assert (hash(Period('2011-01', freq='M')) !=
|
||
|
hash(Period('2011-02', freq='M')))
|
||
|
|
||
|
def test_repr(self):
|
||
|
p = Period('Jan-2000')
|
||
|
assert '2000-01' in repr(p)
|
||
|
|
||
|
p = Period('2000-12-15')
|
||
|
assert '2000-12-15' in repr(p)
|
||
|
|
||
|
def test_repr_nat(self):
|
||
|
p = Period('nat', freq='M')
|
||
|
assert repr(tslib.NaT) in repr(p)
|
||
|
|
||
|
def test_millisecond_repr(self):
|
||
|
p = Period('2000-01-01 12:15:02.123')
|
||
|
|
||
|
assert repr(p) == "Period('2000-01-01 12:15:02.123', 'L')"
|
||
|
|
||
|
def test_microsecond_repr(self):
|
||
|
p = Period('2000-01-01 12:15:02.123567')
|
||
|
|
||
|
assert repr(p) == "Period('2000-01-01 12:15:02.123567', 'U')"
|
||
|
|
||
|
def test_strftime(self):
|
||
|
p = Period('2000-1-1 12:34:12', freq='S')
|
||
|
res = p.strftime('%Y-%m-%d %H:%M:%S')
|
||
|
assert res == '2000-01-01 12:34:12'
|
||
|
assert isinstance(res, text_type) # GH3363
|
||
|
|
||
|
def test_sub_delta(self):
|
||
|
left, right = Period('2011', freq='A'), Period('2007', freq='A')
|
||
|
result = left - right
|
||
|
assert result == 4
|
||
|
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
left - Period('2007-01', freq='M')
|
||
|
|
||
|
def test_to_timestamp(self):
|
||
|
p = Period('1982', freq='A')
|
||
|
start_ts = p.to_timestamp(how='S')
|
||
|
aliases = ['s', 'StarT', 'BEGIn']
|
||
|
for a in aliases:
|
||
|
assert start_ts == p.to_timestamp('D', how=a)
|
||
|
# freq with mult should not affect to the result
|
||
|
assert start_ts == p.to_timestamp('3D', how=a)
|
||
|
|
||
|
end_ts = p.to_timestamp(how='E')
|
||
|
aliases = ['e', 'end', 'FINIsH']
|
||
|
for a in aliases:
|
||
|
assert end_ts == p.to_timestamp('D', how=a)
|
||
|
assert end_ts == p.to_timestamp('3D', how=a)
|
||
|
|
||
|
from_lst = ['A', 'Q', 'M', 'W', 'B', 'D', 'H', 'Min', 'S']
|
||
|
|
||
|
def _ex(p):
|
||
|
return Timestamp((p + 1).start_time.value - 1)
|
||
|
|
||
|
for i, fcode in enumerate(from_lst):
|
||
|
p = Period('1982', freq=fcode)
|
||
|
result = p.to_timestamp().to_period(fcode)
|
||
|
assert result == p
|
||
|
|
||
|
assert p.start_time == p.to_timestamp(how='S')
|
||
|
|
||
|
assert p.end_time == _ex(p)
|
||
|
|
||
|
# Frequency other than daily
|
||
|
|
||
|
p = Period('1985', freq='A')
|
||
|
|
||
|
result = p.to_timestamp('H', how='end')
|
||
|
expected = datetime(1985, 12, 31, 23)
|
||
|
assert result == expected
|
||
|
result = p.to_timestamp('3H', how='end')
|
||
|
assert result == expected
|
||
|
|
||
|
result = p.to_timestamp('T', how='end')
|
||
|
expected = datetime(1985, 12, 31, 23, 59)
|
||
|
assert result == expected
|
||
|
result = p.to_timestamp('2T', how='end')
|
||
|
assert result == expected
|
||
|
|
||
|
result = p.to_timestamp(how='end')
|
||
|
expected = datetime(1985, 12, 31)
|
||
|
assert result == expected
|
||
|
|
||
|
expected = datetime(1985, 1, 1)
|
||
|
result = p.to_timestamp('H', how='start')
|
||
|
assert result == expected
|
||
|
result = p.to_timestamp('T', how='start')
|
||
|
assert result == expected
|
||
|
result = p.to_timestamp('S', how='start')
|
||
|
assert result == expected
|
||
|
result = p.to_timestamp('3H', how='start')
|
||
|
assert result == expected
|
||
|
result = p.to_timestamp('5S', how='start')
|
||
|
assert result == expected
|
||
|
|
||
|
def test_start_time(self):
|
||
|
freq_lst = ['A', 'Q', 'M', 'D', 'H', 'T', 'S']
|
||
|
xp = datetime(2012, 1, 1)
|
||
|
for f in freq_lst:
|
||
|
p = Period('2012', freq=f)
|
||
|
assert p.start_time == xp
|
||
|
assert Period('2012', freq='B').start_time == datetime(2012, 1, 2)
|
||
|
assert Period('2012', freq='W').start_time == datetime(2011, 12, 26)
|
||
|
|
||
|
def test_end_time(self):
|
||
|
p = Period('2012', freq='A')
|
||
|
|
||
|
def _ex(*args):
|
||
|
return Timestamp(Timestamp(datetime(*args)).value - 1)
|
||
|
|
||
|
xp = _ex(2013, 1, 1)
|
||
|
assert xp == p.end_time
|
||
|
|
||
|
p = Period('2012', freq='Q')
|
||
|
xp = _ex(2012, 4, 1)
|
||
|
assert xp == p.end_time
|
||
|
|
||
|
p = Period('2012', freq='M')
|
||
|
xp = _ex(2012, 2, 1)
|
||
|
assert xp == p.end_time
|
||
|
|
||
|
p = Period('2012', freq='D')
|
||
|
xp = _ex(2012, 1, 2)
|
||
|
assert xp == p.end_time
|
||
|
|
||
|
p = Period('2012', freq='H')
|
||
|
xp = _ex(2012, 1, 1, 1)
|
||
|
assert xp == p.end_time
|
||
|
|
||
|
p = Period('2012', freq='B')
|
||
|
xp = _ex(2012, 1, 3)
|
||
|
assert xp == p.end_time
|
||
|
|
||
|
p = Period('2012', freq='W')
|
||
|
xp = _ex(2012, 1, 2)
|
||
|
assert xp == p.end_time
|
||
|
|
||
|
# Test for GH 11738
|
||
|
p = Period('2012', freq='15D')
|
||
|
xp = _ex(2012, 1, 16)
|
||
|
assert xp == p.end_time
|
||
|
|
||
|
p = Period('2012', freq='1D1H')
|
||
|
xp = _ex(2012, 1, 2, 1)
|
||
|
assert xp == p.end_time
|
||
|
|
||
|
p = Period('2012', freq='1H1D')
|
||
|
xp = _ex(2012, 1, 2, 1)
|
||
|
assert xp == p.end_time
|
||
|
|
||
|
def test_anchor_week_end_time(self):
|
||
|
def _ex(*args):
|
||
|
return Timestamp(Timestamp(datetime(*args)).value - 1)
|
||
|
|
||
|
p = Period('2013-1-1', 'W-SAT')
|
||
|
xp = _ex(2013, 1, 6)
|
||
|
assert p.end_time == xp
|
||
|
|
||
|
def test_properties_annually(self):
|
||
|
# Test properties on Periods with annually frequency.
|
||
|
a_date = Period(freq='A', year=2007)
|
||
|
assert a_date.year == 2007
|
||
|
|
||
|
def test_properties_quarterly(self):
|
||
|
# Test properties on Periods with daily frequency.
|
||
|
qedec_date = Period(freq="Q-DEC", year=2007, quarter=1)
|
||
|
qejan_date = Period(freq="Q-JAN", year=2007, quarter=1)
|
||
|
qejun_date = Period(freq="Q-JUN", year=2007, quarter=1)
|
||
|
#
|
||
|
for x in range(3):
|
||
|
for qd in (qedec_date, qejan_date, qejun_date):
|
||
|
assert (qd + x).qyear == 2007
|
||
|
assert (qd + x).quarter == x + 1
|
||
|
|
||
|
def test_properties_monthly(self):
|
||
|
# Test properties on Periods with daily frequency.
|
||
|
m_date = Period(freq='M', year=2007, month=1)
|
||
|
for x in range(11):
|
||
|
m_ival_x = m_date + x
|
||
|
assert m_ival_x.year == 2007
|
||
|
if 1 <= x + 1 <= 3:
|
||
|
assert m_ival_x.quarter == 1
|
||
|
elif 4 <= x + 1 <= 6:
|
||
|
assert m_ival_x.quarter == 2
|
||
|
elif 7 <= x + 1 <= 9:
|
||
|
assert m_ival_x.quarter == 3
|
||
|
elif 10 <= x + 1 <= 12:
|
||
|
assert m_ival_x.quarter == 4
|
||
|
assert m_ival_x.month == x + 1
|
||
|
|
||
|
def test_properties_weekly(self):
|
||
|
# Test properties on Periods with daily frequency.
|
||
|
w_date = Period(freq='W', year=2007, month=1, day=7)
|
||
|
#
|
||
|
assert w_date.year == 2007
|
||
|
assert w_date.quarter == 1
|
||
|
assert w_date.month == 1
|
||
|
assert w_date.week == 1
|
||
|
assert (w_date - 1).week == 52
|
||
|
assert w_date.days_in_month == 31
|
||
|
assert Period(freq='W', year=2012,
|
||
|
month=2, day=1).days_in_month == 29
|
||
|
|
||
|
def test_properties_weekly_legacy(self):
|
||
|
# Test properties on Periods with daily frequency.
|
||
|
w_date = Period(freq='W', year=2007, month=1, day=7)
|
||
|
assert w_date.year == 2007
|
||
|
assert w_date.quarter == 1
|
||
|
assert w_date.month == 1
|
||
|
assert w_date.week == 1
|
||
|
assert (w_date - 1).week == 52
|
||
|
assert w_date.days_in_month == 31
|
||
|
|
||
|
exp = Period(freq='W', year=2012, month=2, day=1)
|
||
|
assert exp.days_in_month == 29
|
||
|
|
||
|
msg = pd._libs.tslibs.frequencies._INVALID_FREQ_ERROR
|
||
|
with tm.assert_raises_regex(ValueError, msg):
|
||
|
Period(freq='WK', year=2007, month=1, day=7)
|
||
|
|
||
|
def test_properties_daily(self):
|
||
|
# Test properties on Periods with daily frequency.
|
||
|
b_date = Period(freq='B', year=2007, month=1, day=1)
|
||
|
#
|
||
|
assert b_date.year == 2007
|
||
|
assert b_date.quarter == 1
|
||
|
assert b_date.month == 1
|
||
|
assert b_date.day == 1
|
||
|
assert b_date.weekday == 0
|
||
|
assert b_date.dayofyear == 1
|
||
|
assert b_date.days_in_month == 31
|
||
|
assert Period(freq='B', year=2012,
|
||
|
month=2, day=1).days_in_month == 29
|
||
|
|
||
|
d_date = Period(freq='D', year=2007, month=1, day=1)
|
||
|
|
||
|
assert d_date.year == 2007
|
||
|
assert d_date.quarter == 1
|
||
|
assert d_date.month == 1
|
||
|
assert d_date.day == 1
|
||
|
assert d_date.weekday == 0
|
||
|
assert d_date.dayofyear == 1
|
||
|
assert d_date.days_in_month == 31
|
||
|
assert Period(freq='D', year=2012, month=2,
|
||
|
day=1).days_in_month == 29
|
||
|
|
||
|
def test_properties_hourly(self):
|
||
|
# Test properties on Periods with hourly frequency.
|
||
|
h_date1 = Period(freq='H', year=2007, month=1, day=1, hour=0)
|
||
|
h_date2 = Period(freq='2H', year=2007, month=1, day=1, hour=0)
|
||
|
|
||
|
for h_date in [h_date1, h_date2]:
|
||
|
assert h_date.year == 2007
|
||
|
assert h_date.quarter == 1
|
||
|
assert h_date.month == 1
|
||
|
assert h_date.day == 1
|
||
|
assert h_date.weekday == 0
|
||
|
assert h_date.dayofyear == 1
|
||
|
assert h_date.hour == 0
|
||
|
assert h_date.days_in_month == 31
|
||
|
assert Period(freq='H', year=2012, month=2, day=1,
|
||
|
hour=0).days_in_month == 29
|
||
|
|
||
|
def test_properties_minutely(self):
|
||
|
# Test properties on Periods with minutely frequency.
|
||
|
t_date = Period(freq='Min', year=2007, month=1, day=1, hour=0,
|
||
|
minute=0)
|
||
|
#
|
||
|
assert t_date.quarter == 1
|
||
|
assert t_date.month == 1
|
||
|
assert t_date.day == 1
|
||
|
assert t_date.weekday == 0
|
||
|
assert t_date.dayofyear == 1
|
||
|
assert t_date.hour == 0
|
||
|
assert t_date.minute == 0
|
||
|
assert t_date.days_in_month == 31
|
||
|
assert Period(freq='D', year=2012, month=2, day=1, hour=0,
|
||
|
minute=0).days_in_month == 29
|
||
|
|
||
|
def test_properties_secondly(self):
|
||
|
# Test properties on Periods with secondly frequency.
|
||
|
s_date = Period(freq='Min', year=2007, month=1, day=1, hour=0,
|
||
|
minute=0, second=0)
|
||
|
#
|
||
|
assert s_date.year == 2007
|
||
|
assert s_date.quarter == 1
|
||
|
assert s_date.month == 1
|
||
|
assert s_date.day == 1
|
||
|
assert s_date.weekday == 0
|
||
|
assert s_date.dayofyear == 1
|
||
|
assert s_date.hour == 0
|
||
|
assert s_date.minute == 0
|
||
|
assert s_date.second == 0
|
||
|
assert s_date.days_in_month == 31
|
||
|
assert Period(freq='Min', year=2012, month=2, day=1, hour=0,
|
||
|
minute=0, second=0).days_in_month == 29
|
||
|
|
||
|
def test_pnow(self):
|
||
|
|
||
|
# deprecation, xref #13790
|
||
|
with tm.assert_produces_warning(FutureWarning,
|
||
|
check_stacklevel=False):
|
||
|
period.pnow('D')
|
||
|
|
||
|
def test_constructor_corner(self):
|
||
|
expected = Period('2007-01', freq='2M')
|
||
|
assert Period(year=2007, month=1, freq='2M') == expected
|
||
|
|
||
|
pytest.raises(ValueError, Period, datetime.now())
|
||
|
pytest.raises(ValueError, Period, datetime.now().date())
|
||
|
pytest.raises(ValueError, Period, 1.6, freq='D')
|
||
|
pytest.raises(ValueError, Period, ordinal=1.6, freq='D')
|
||
|
pytest.raises(ValueError, Period, ordinal=2, value=1, freq='D')
|
||
|
assert Period(None) is pd.NaT
|
||
|
pytest.raises(ValueError, Period, month=1)
|
||
|
|
||
|
p = Period('2007-01-01', freq='D')
|
||
|
|
||
|
result = Period(p, freq='A')
|
||
|
exp = Period('2007', freq='A')
|
||
|
assert result == exp
|
||
|
|
||
|
def test_constructor_infer_freq(self):
|
||
|
p = Period('2007-01-01')
|
||
|
assert p.freq == 'D'
|
||
|
|
||
|
p = Period('2007-01-01 07')
|
||
|
assert p.freq == 'H'
|
||
|
|
||
|
p = Period('2007-01-01 07:10')
|
||
|
assert p.freq == 'T'
|
||
|
|
||
|
p = Period('2007-01-01 07:10:15')
|
||
|
assert p.freq == 'S'
|
||
|
|
||
|
p = Period('2007-01-01 07:10:15.123')
|
||
|
assert p.freq == 'L'
|
||
|
|
||
|
p = Period('2007-01-01 07:10:15.123000')
|
||
|
assert p.freq == 'L'
|
||
|
|
||
|
p = Period('2007-01-01 07:10:15.123400')
|
||
|
assert p.freq == 'U'
|
||
|
|
||
|
def test_badinput(self):
|
||
|
pytest.raises(ValueError, Period, '-2000', 'A')
|
||
|
pytest.raises(DateParseError, Period, '0', 'A')
|
||
|
pytest.raises(DateParseError, Period, '1/1/-2000', 'A')
|
||
|
|
||
|
def test_multiples(self):
|
||
|
result1 = Period('1989', freq='2A')
|
||
|
result2 = Period('1989', freq='A')
|
||
|
assert result1.ordinal == result2.ordinal
|
||
|
assert result1.freqstr == '2A-DEC'
|
||
|
assert result2.freqstr == 'A-DEC'
|
||
|
assert result1.freq == offsets.YearEnd(2)
|
||
|
assert result2.freq == offsets.YearEnd()
|
||
|
|
||
|
assert (result1 + 1).ordinal == result1.ordinal + 2
|
||
|
assert (1 + result1).ordinal == result1.ordinal + 2
|
||
|
assert (result1 - 1).ordinal == result2.ordinal - 2
|
||
|
assert (-1 + result1).ordinal == result2.ordinal - 2
|
||
|
|
||
|
def test_round_trip(self):
|
||
|
|
||
|
p = Period('2000Q1')
|
||
|
new_p = tm.round_trip_pickle(p)
|
||
|
assert new_p == p
|
||
|
|
||
|
|
||
|
class TestPeriodField(object):
|
||
|
|
||
|
def test_get_period_field_array_raises_on_out_of_range(self):
|
||
|
pytest.raises(ValueError, libperiod.get_period_field_arr, -1,
|
||
|
np.empty(1), 0)
|
||
|
|
||
|
|
||
|
class TestComparisons(object):
|
||
|
|
||
|
def setup_method(self, method):
|
||
|
self.january1 = Period('2000-01', 'M')
|
||
|
self.january2 = Period('2000-01', 'M')
|
||
|
self.february = Period('2000-02', 'M')
|
||
|
self.march = Period('2000-03', 'M')
|
||
|
self.day = Period('2012-01-01', 'D')
|
||
|
|
||
|
def test_equal(self):
|
||
|
assert self.january1 == self.january2
|
||
|
|
||
|
def test_equal_Raises_Value(self):
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
self.january1 == self.day
|
||
|
|
||
|
def test_notEqual(self):
|
||
|
assert self.january1 != 1
|
||
|
assert self.january1 != self.february
|
||
|
|
||
|
def test_greater(self):
|
||
|
assert self.february > self.january1
|
||
|
|
||
|
def test_greater_Raises_Value(self):
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
self.january1 > self.day
|
||
|
|
||
|
def test_greater_Raises_Type(self):
|
||
|
with pytest.raises(TypeError):
|
||
|
self.january1 > 1
|
||
|
|
||
|
def test_greaterEqual(self):
|
||
|
assert self.january1 >= self.january2
|
||
|
|
||
|
def test_greaterEqual_Raises_Value(self):
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
self.january1 >= self.day
|
||
|
|
||
|
with pytest.raises(TypeError):
|
||
|
print(self.january1 >= 1)
|
||
|
|
||
|
def test_smallerEqual(self):
|
||
|
assert self.january1 <= self.january2
|
||
|
|
||
|
def test_smallerEqual_Raises_Value(self):
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
self.january1 <= self.day
|
||
|
|
||
|
def test_smallerEqual_Raises_Type(self):
|
||
|
with pytest.raises(TypeError):
|
||
|
self.january1 <= 1
|
||
|
|
||
|
def test_smaller(self):
|
||
|
assert self.january1 < self.february
|
||
|
|
||
|
def test_smaller_Raises_Value(self):
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
self.january1 < self.day
|
||
|
|
||
|
def test_smaller_Raises_Type(self):
|
||
|
with pytest.raises(TypeError):
|
||
|
self.january1 < 1
|
||
|
|
||
|
def test_sort(self):
|
||
|
periods = [self.march, self.january1, self.february]
|
||
|
correctPeriods = [self.january1, self.february, self.march]
|
||
|
assert sorted(periods) == correctPeriods
|
||
|
|
||
|
def test_period_nat_comp(self):
|
||
|
p_nat = Period('NaT', freq='D')
|
||
|
p = Period('2011-01-01', freq='D')
|
||
|
|
||
|
nat = pd.Timestamp('NaT')
|
||
|
t = pd.Timestamp('2011-01-01')
|
||
|
# confirm Period('NaT') work identical with Timestamp('NaT')
|
||
|
for left, right in [(p_nat, p), (p, p_nat), (p_nat, p_nat), (nat, t),
|
||
|
(t, nat), (nat, nat)]:
|
||
|
assert not left < right
|
||
|
assert not left > right
|
||
|
assert not left == right
|
||
|
assert left != right
|
||
|
assert not left <= right
|
||
|
assert not left >= right
|
||
|
|
||
|
|
||
|
class TestMethods(object):
|
||
|
|
||
|
def test_add(self):
|
||
|
dt1 = Period(freq='D', year=2008, month=1, day=1)
|
||
|
dt2 = Period(freq='D', year=2008, month=1, day=2)
|
||
|
assert dt1 + 1 == dt2
|
||
|
assert 1 + dt1 == dt2
|
||
|
|
||
|
def test_add_pdnat(self):
|
||
|
p = pd.Period('2011-01', freq='M')
|
||
|
assert p + pd.NaT is pd.NaT
|
||
|
assert pd.NaT + p is pd.NaT
|
||
|
|
||
|
p = pd.Period('NaT', freq='M')
|
||
|
assert p + pd.NaT is pd.NaT
|
||
|
assert pd.NaT + p is pd.NaT
|
||
|
|
||
|
def test_add_raises(self):
|
||
|
# GH 4731
|
||
|
dt1 = Period(freq='D', year=2008, month=1, day=1)
|
||
|
dt2 = Period(freq='D', year=2008, month=1, day=2)
|
||
|
msg = r"unsupported operand type\(s\)"
|
||
|
with tm.assert_raises_regex(TypeError, msg):
|
||
|
dt1 + "str"
|
||
|
|
||
|
msg = r"unsupported operand type\(s\)"
|
||
|
with tm.assert_raises_regex(TypeError, msg):
|
||
|
"str" + dt1
|
||
|
|
||
|
with tm.assert_raises_regex(TypeError, msg):
|
||
|
dt1 + dt2
|
||
|
|
||
|
boxes = [lambda x: x, lambda x: pd.Series([x]), lambda x: pd.Index([x])]
|
||
|
|
||
|
@pytest.mark.parametrize('lbox', boxes)
|
||
|
@pytest.mark.parametrize('rbox', boxes)
|
||
|
def test_add_timestamp_raises(self, rbox, lbox):
|
||
|
# GH # 17983
|
||
|
ts = pd.Timestamp('2017')
|
||
|
per = pd.Period('2017', freq='M')
|
||
|
|
||
|
# We may get a different message depending on which class raises
|
||
|
# the error.
|
||
|
msg = (r"cannot add|unsupported operand|"
|
||
|
r"can only operate on a|incompatible type|"
|
||
|
r"ufunc add cannot use operands")
|
||
|
with tm.assert_raises_regex(TypeError, msg):
|
||
|
lbox(ts) + rbox(per)
|
||
|
|
||
|
with tm.assert_raises_regex(TypeError, msg):
|
||
|
lbox(per) + rbox(ts)
|
||
|
|
||
|
with tm.assert_raises_regex(TypeError, msg):
|
||
|
lbox(per) + rbox(per)
|
||
|
|
||
|
def test_sub(self):
|
||
|
dt1 = Period('2011-01-01', freq='D')
|
||
|
dt2 = Period('2011-01-15', freq='D')
|
||
|
|
||
|
assert dt1 - dt2 == -14
|
||
|
assert dt2 - dt1 == 14
|
||
|
|
||
|
msg = r"Input has different freq=M from Period\(freq=D\)"
|
||
|
with tm.assert_raises_regex(period.IncompatibleFrequency, msg):
|
||
|
dt1 - pd.Period('2011-02', freq='M')
|
||
|
|
||
|
def test_add_offset(self):
|
||
|
# freq is DateOffset
|
||
|
for freq in ['A', '2A', '3A']:
|
||
|
p = Period('2011', freq=freq)
|
||
|
exp = Period('2013', freq=freq)
|
||
|
assert p + offsets.YearEnd(2) == exp
|
||
|
assert offsets.YearEnd(2) + p == exp
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(365, 'D'),
|
||
|
timedelta(365)]:
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
p + o
|
||
|
|
||
|
if isinstance(o, np.timedelta64):
|
||
|
with pytest.raises(TypeError):
|
||
|
o + p
|
||
|
else:
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
o + p
|
||
|
|
||
|
for freq in ['M', '2M', '3M']:
|
||
|
p = Period('2011-03', freq=freq)
|
||
|
exp = Period('2011-05', freq=freq)
|
||
|
assert p + offsets.MonthEnd(2) == exp
|
||
|
assert offsets.MonthEnd(2) + p == exp
|
||
|
|
||
|
exp = Period('2012-03', freq=freq)
|
||
|
assert p + offsets.MonthEnd(12) == exp
|
||
|
assert offsets.MonthEnd(12) + p == exp
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(365, 'D'),
|
||
|
timedelta(365)]:
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
p + o
|
||
|
|
||
|
if isinstance(o, np.timedelta64):
|
||
|
with pytest.raises(TypeError):
|
||
|
o + p
|
||
|
else:
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
o + p
|
||
|
|
||
|
# freq is Tick
|
||
|
for freq in ['D', '2D', '3D']:
|
||
|
p = Period('2011-04-01', freq=freq)
|
||
|
|
||
|
exp = Period('2011-04-06', freq=freq)
|
||
|
assert p + offsets.Day(5) == exp
|
||
|
assert offsets.Day(5) + p == exp
|
||
|
|
||
|
exp = Period('2011-04-02', freq=freq)
|
||
|
assert p + offsets.Hour(24) == exp
|
||
|
assert offsets.Hour(24) + p == exp
|
||
|
|
||
|
exp = Period('2011-04-03', freq=freq)
|
||
|
assert p + np.timedelta64(2, 'D') == exp
|
||
|
with pytest.raises(TypeError):
|
||
|
np.timedelta64(2, 'D') + p
|
||
|
|
||
|
exp = Period('2011-04-02', freq=freq)
|
||
|
assert p + np.timedelta64(3600 * 24, 's') == exp
|
||
|
with pytest.raises(TypeError):
|
||
|
np.timedelta64(3600 * 24, 's') + p
|
||
|
|
||
|
exp = Period('2011-03-30', freq=freq)
|
||
|
assert p + timedelta(-2) == exp
|
||
|
assert timedelta(-2) + p == exp
|
||
|
|
||
|
exp = Period('2011-04-03', freq=freq)
|
||
|
assert p + timedelta(hours=48) == exp
|
||
|
assert timedelta(hours=48) + p == exp
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(4, 'h'),
|
||
|
timedelta(hours=23)]:
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
p + o
|
||
|
|
||
|
if isinstance(o, np.timedelta64):
|
||
|
with pytest.raises(TypeError):
|
||
|
o + p
|
||
|
else:
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
o + p
|
||
|
|
||
|
for freq in ['H', '2H', '3H']:
|
||
|
p = Period('2011-04-01 09:00', freq=freq)
|
||
|
|
||
|
exp = Period('2011-04-03 09:00', freq=freq)
|
||
|
assert p + offsets.Day(2) == exp
|
||
|
assert offsets.Day(2) + p == exp
|
||
|
|
||
|
exp = Period('2011-04-01 12:00', freq=freq)
|
||
|
assert p + offsets.Hour(3) == exp
|
||
|
assert offsets.Hour(3) + p == exp
|
||
|
|
||
|
exp = Period('2011-04-01 12:00', freq=freq)
|
||
|
assert p + np.timedelta64(3, 'h') == exp
|
||
|
with pytest.raises(TypeError):
|
||
|
np.timedelta64(3, 'h') + p
|
||
|
|
||
|
exp = Period('2011-04-01 10:00', freq=freq)
|
||
|
assert p + np.timedelta64(3600, 's') == exp
|
||
|
with pytest.raises(TypeError):
|
||
|
np.timedelta64(3600, 's') + p
|
||
|
|
||
|
exp = Period('2011-04-01 11:00', freq=freq)
|
||
|
assert p + timedelta(minutes=120) == exp
|
||
|
assert timedelta(minutes=120) + p == exp
|
||
|
|
||
|
exp = Period('2011-04-05 12:00', freq=freq)
|
||
|
assert p + timedelta(days=4, minutes=180) == exp
|
||
|
assert timedelta(days=4, minutes=180) + p == exp
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(3200, 's'),
|
||
|
timedelta(hours=23, minutes=30)]:
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
p + o
|
||
|
|
||
|
if isinstance(o, np.timedelta64):
|
||
|
with pytest.raises(TypeError):
|
||
|
o + p
|
||
|
else:
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
o + p
|
||
|
|
||
|
def test_add_offset_nat(self):
|
||
|
# freq is DateOffset
|
||
|
for freq in ['A', '2A', '3A']:
|
||
|
p = Period('NaT', freq=freq)
|
||
|
for o in [offsets.YearEnd(2)]:
|
||
|
assert p + o is tslib.NaT
|
||
|
assert o + p is tslib.NaT
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(365, 'D'),
|
||
|
timedelta(365)]:
|
||
|
assert p + o is tslib.NaT
|
||
|
|
||
|
if isinstance(o, np.timedelta64):
|
||
|
with pytest.raises(TypeError):
|
||
|
o + p
|
||
|
else:
|
||
|
assert o + p is tslib.NaT
|
||
|
|
||
|
for freq in ['M', '2M', '3M']:
|
||
|
p = Period('NaT', freq=freq)
|
||
|
for o in [offsets.MonthEnd(2), offsets.MonthEnd(12)]:
|
||
|
assert p + o is tslib.NaT
|
||
|
|
||
|
if isinstance(o, np.timedelta64):
|
||
|
with pytest.raises(TypeError):
|
||
|
o + p
|
||
|
else:
|
||
|
assert o + p is tslib.NaT
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(365, 'D'),
|
||
|
timedelta(365)]:
|
||
|
assert p + o is tslib.NaT
|
||
|
|
||
|
if isinstance(o, np.timedelta64):
|
||
|
with pytest.raises(TypeError):
|
||
|
o + p
|
||
|
else:
|
||
|
assert o + p is tslib.NaT
|
||
|
|
||
|
# freq is Tick
|
||
|
for freq in ['D', '2D', '3D']:
|
||
|
p = Period('NaT', freq=freq)
|
||
|
for o in [offsets.Day(5), offsets.Hour(24), np.timedelta64(2, 'D'),
|
||
|
np.timedelta64(3600 * 24, 's'), timedelta(-2),
|
||
|
timedelta(hours=48)]:
|
||
|
assert p + o is tslib.NaT
|
||
|
|
||
|
if isinstance(o, np.timedelta64):
|
||
|
with pytest.raises(TypeError):
|
||
|
o + p
|
||
|
else:
|
||
|
assert o + p is tslib.NaT
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(4, 'h'),
|
||
|
timedelta(hours=23)]:
|
||
|
assert p + o is tslib.NaT
|
||
|
|
||
|
if isinstance(o, np.timedelta64):
|
||
|
with pytest.raises(TypeError):
|
||
|
o + p
|
||
|
else:
|
||
|
assert o + p is tslib.NaT
|
||
|
|
||
|
for freq in ['H', '2H', '3H']:
|
||
|
p = Period('NaT', freq=freq)
|
||
|
for o in [offsets.Day(2), offsets.Hour(3), np.timedelta64(3, 'h'),
|
||
|
np.timedelta64(3600, 's'), timedelta(minutes=120),
|
||
|
timedelta(days=4, minutes=180)]:
|
||
|
assert p + o is tslib.NaT
|
||
|
|
||
|
if not isinstance(o, np.timedelta64):
|
||
|
assert o + p is tslib.NaT
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(3200, 's'),
|
||
|
timedelta(hours=23, minutes=30)]:
|
||
|
assert p + o is tslib.NaT
|
||
|
|
||
|
if isinstance(o, np.timedelta64):
|
||
|
with pytest.raises(TypeError):
|
||
|
o + p
|
||
|
else:
|
||
|
assert o + p is tslib.NaT
|
||
|
|
||
|
def test_sub_pdnat(self):
|
||
|
# GH 13071
|
||
|
p = pd.Period('2011-01', freq='M')
|
||
|
assert p - pd.NaT is pd.NaT
|
||
|
assert pd.NaT - p is pd.NaT
|
||
|
|
||
|
p = pd.Period('NaT', freq='M')
|
||
|
assert p - pd.NaT is pd.NaT
|
||
|
assert pd.NaT - p is pd.NaT
|
||
|
|
||
|
def test_sub_offset(self):
|
||
|
# freq is DateOffset
|
||
|
for freq in ['A', '2A', '3A']:
|
||
|
p = Period('2011', freq=freq)
|
||
|
assert p - offsets.YearEnd(2) == Period('2009', freq=freq)
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(365, 'D'),
|
||
|
timedelta(365)]:
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
p - o
|
||
|
|
||
|
for freq in ['M', '2M', '3M']:
|
||
|
p = Period('2011-03', freq=freq)
|
||
|
assert p - offsets.MonthEnd(2) == Period('2011-01', freq=freq)
|
||
|
assert p - offsets.MonthEnd(12) == Period('2010-03', freq=freq)
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(365, 'D'),
|
||
|
timedelta(365)]:
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
p - o
|
||
|
|
||
|
# freq is Tick
|
||
|
for freq in ['D', '2D', '3D']:
|
||
|
p = Period('2011-04-01', freq=freq)
|
||
|
assert p - offsets.Day(5) == Period('2011-03-27', freq=freq)
|
||
|
assert p - offsets.Hour(24) == Period('2011-03-31', freq=freq)
|
||
|
assert p - np.timedelta64(2, 'D') == Period(
|
||
|
'2011-03-30', freq=freq)
|
||
|
assert p - np.timedelta64(3600 * 24, 's') == Period(
|
||
|
'2011-03-31', freq=freq)
|
||
|
assert p - timedelta(-2) == Period('2011-04-03', freq=freq)
|
||
|
assert p - timedelta(hours=48) == Period('2011-03-30', freq=freq)
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(4, 'h'),
|
||
|
timedelta(hours=23)]:
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
p - o
|
||
|
|
||
|
for freq in ['H', '2H', '3H']:
|
||
|
p = Period('2011-04-01 09:00', freq=freq)
|
||
|
assert p - offsets.Day(2) == Period('2011-03-30 09:00', freq=freq)
|
||
|
assert p - offsets.Hour(3) == Period('2011-04-01 06:00', freq=freq)
|
||
|
assert p - np.timedelta64(3, 'h') == Period(
|
||
|
'2011-04-01 06:00', freq=freq)
|
||
|
assert p - np.timedelta64(3600, 's') == Period(
|
||
|
'2011-04-01 08:00', freq=freq)
|
||
|
assert p - timedelta(minutes=120) == Period(
|
||
|
'2011-04-01 07:00', freq=freq)
|
||
|
assert p - timedelta(days=4, minutes=180) == Period(
|
||
|
'2011-03-28 06:00', freq=freq)
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(3200, 's'),
|
||
|
timedelta(hours=23, minutes=30)]:
|
||
|
with pytest.raises(period.IncompatibleFrequency):
|
||
|
p - o
|
||
|
|
||
|
def test_sub_offset_nat(self):
|
||
|
# freq is DateOffset
|
||
|
for freq in ['A', '2A', '3A']:
|
||
|
p = Period('NaT', freq=freq)
|
||
|
for o in [offsets.YearEnd(2)]:
|
||
|
assert p - o is tslib.NaT
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(365, 'D'),
|
||
|
timedelta(365)]:
|
||
|
assert p - o is tslib.NaT
|
||
|
|
||
|
for freq in ['M', '2M', '3M']:
|
||
|
p = Period('NaT', freq=freq)
|
||
|
for o in [offsets.MonthEnd(2), offsets.MonthEnd(12)]:
|
||
|
assert p - o is tslib.NaT
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(365, 'D'),
|
||
|
timedelta(365)]:
|
||
|
assert p - o is tslib.NaT
|
||
|
|
||
|
# freq is Tick
|
||
|
for freq in ['D', '2D', '3D']:
|
||
|
p = Period('NaT', freq=freq)
|
||
|
for o in [offsets.Day(5), offsets.Hour(24), np.timedelta64(2, 'D'),
|
||
|
np.timedelta64(3600 * 24, 's'), timedelta(-2),
|
||
|
timedelta(hours=48)]:
|
||
|
assert p - o is tslib.NaT
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(4, 'h'),
|
||
|
timedelta(hours=23)]:
|
||
|
assert p - o is tslib.NaT
|
||
|
|
||
|
for freq in ['H', '2H', '3H']:
|
||
|
p = Period('NaT', freq=freq)
|
||
|
for o in [offsets.Day(2), offsets.Hour(3), np.timedelta64(3, 'h'),
|
||
|
np.timedelta64(3600, 's'), timedelta(minutes=120),
|
||
|
timedelta(days=4, minutes=180)]:
|
||
|
assert p - o is tslib.NaT
|
||
|
|
||
|
for o in [offsets.YearBegin(2), offsets.MonthBegin(1),
|
||
|
offsets.Minute(), np.timedelta64(3200, 's'),
|
||
|
timedelta(hours=23, minutes=30)]:
|
||
|
assert p - o is tslib.NaT
|
||
|
|
||
|
@pytest.mark.parametrize('freq', ['M', '2M', '3M'])
|
||
|
def test_nat_ops(self, freq):
|
||
|
p = Period('NaT', freq=freq)
|
||
|
assert p + 1 is tslib.NaT
|
||
|
assert 1 + p is tslib.NaT
|
||
|
assert p - 1 is tslib.NaT
|
||
|
assert p - Period('2011-01', freq=freq) is tslib.NaT
|
||
|
assert Period('2011-01', freq=freq) - p is tslib.NaT
|
||
|
|
||
|
def test_period_ops_offset(self):
|
||
|
p = Period('2011-04-01', freq='D')
|
||
|
result = p + offsets.Day()
|
||
|
exp = pd.Period('2011-04-02', freq='D')
|
||
|
assert result == exp
|
||
|
|
||
|
result = p - offsets.Day(2)
|
||
|
exp = pd.Period('2011-03-30', freq='D')
|
||
|
assert result == exp
|
||
|
|
||
|
msg = r"Input cannot be converted to Period\(freq=D\)"
|
||
|
with tm.assert_raises_regex(period.IncompatibleFrequency, msg):
|
||
|
p + offsets.Hour(2)
|
||
|
|
||
|
with tm.assert_raises_regex(period.IncompatibleFrequency, msg):
|
||
|
p - offsets.Hour(2)
|
||
|
|
||
|
|
||
|
def test_period_immutable():
|
||
|
# see gh-17116
|
||
|
per = pd.Period('2014Q1')
|
||
|
with pytest.raises(AttributeError):
|
||
|
per.ordinal = 14
|
||
|
|
||
|
freq = per.freq
|
||
|
with pytest.raises(AttributeError):
|
||
|
per.freq = 2 * freq
|
||
|
|
||
|
|
||
|
@pytest.mark.xfail(reason='GH#19834 Period parsing error')
|
||
|
def test_small_year_parsing():
|
||
|
per1 = Period('0001-01-07', 'D')
|
||
|
assert per1.year == 1
|
||
|
assert per1.day == 7
|