def test_datetime_difference(self): """ Test `datetime64 - datetime64`. """ sub = self.jit(sub_usecase) def check(a, b, expected=None): with self.silence_numpy_warnings(): self.assertPreciseEqual(sub(a, b), a - b, (a, b)) self.assertPreciseEqual(sub(b, a), b - a, (a, b)) # Did we get it right? self.assertPreciseEqual(a - b, expected) check(DT('2014'), DT('2017'), TD(-3, 'Y')) check(DT('2014-02'), DT('2017-01'), TD(-35, 'M')) check(DT('2014-02-28'), DT('2015-03-01'), TD(-366, 'D')) # NaTs check(DT('NaT', 'M'), DT('2000'), TD('NaT', 'M')) check(DT('NaT', 'M'), DT('2000-01-01'), TD('NaT', 'D')) check(DT('NaT'), DT('NaT'), TD('NaT')) # Test many more values with self.silence_numpy_warnings(): dts = self.datetime_samples() for a, b in itertools.product(dts, dts): if (not npdatetime_helpers.same_kind(value_unit(a), value_unit(b))): continue self.assertPreciseEqual(sub(a, b), a - b, (a, b))
def test_comparisons(self): # Test all datetime comparisons all at once eq = self.jit(eq_usecase) ne = self.jit(ne_usecase) lt = self.jit(lt_usecase) le = self.jit(le_usecase) gt = self.jit(gt_usecase) ge = self.jit(ge_usecase) def check_eq(a, b, expected): expected_val = expected not_expected_val = not expected if numpy_version >= (1, 16): # since np 1.16 all NaT comparisons bar != are False, including # NaT==NaT if np.isnat(a) or np.isnat(b): expected_val = False not_expected_val = True self.assertFalse(le(a, b), (a, b)) self.assertFalse(ge(a, b), (a, b)) self.assertFalse(le(b, a), (a, b)) self.assertFalse(ge(b, a), (a, b)) self.assertFalse(lt(a, b), (a, b)) self.assertFalse(gt(a, b), (a, b)) self.assertFalse(lt(b, a), (a, b)) self.assertFalse(gt(b, a), (a, b)) with self.silence_numpy_warnings(): self.assertPreciseEqual(eq(a, b), expected_val, (a, b, expected)) self.assertPreciseEqual(eq(b, a), expected_val, (a, b, expected)) self.assertPreciseEqual(ne(a, b), not_expected_val, (a, b, expected)) self.assertPreciseEqual(ne(b, a), not_expected_val, (a, b, expected)) if expected_val: # If equal, then equal-ordered comparisons are true self.assertTrue(le(a, b), (a, b)) self.assertTrue(ge(a, b), (a, b)) self.assertTrue(le(b, a), (a, b)) self.assertTrue(ge(b, a), (a, b)) # and strictly ordered comparisons are false self.assertFalse(lt(a, b), (a, b)) self.assertFalse(gt(a, b), (a, b)) self.assertFalse(lt(b, a), (a, b)) self.assertFalse(gt(b, a), (a, b)) # Did we get it right? self.assertPreciseEqual(a == b, expected_val) def check_lt(a, b, expected): expected_val = expected not_expected_val = not expected if numpy_version >= (1, 16): # since np 1.16 all NaT magnitude comparisons including equality # are False (as NaT == NaT is now False) if np.isnat(a) or np.isnat(b): expected_val = False not_expected_val = False with self.silence_numpy_warnings(): lt = self.jit(lt_usecase) self.assertPreciseEqual(lt(a, b), expected_val, (a, b, expected)) self.assertPreciseEqual(gt(b, a), expected_val, (a, b, expected)) self.assertPreciseEqual(ge(a, b), not_expected_val, (a, b, expected)) self.assertPreciseEqual(le(b, a), not_expected_val, (a, b, expected)) if expected_val: # If true, then values are not equal check_eq(a, b, False) # Did we get it right? self.assertPreciseEqual(a < b, expected_val) check_eq(DT('2014'), DT('2017'), False) check_eq(DT('2014'), DT('2014-01'), True) check_eq(DT('2014'), DT('2014-01-01'), True) check_eq(DT('2014'), DT('2014-01-01', 'W'), True) check_eq(DT('2014-01'), DT('2014-01-01', 'W'), True) # Yes, it's not transitive check_eq(DT('2014-01-01'), DT('2014-01-01', 'W'), False) check_eq(DT('2014-01-02'), DT('2014-01-06', 'W'), True) # with times check_eq(DT('2014-01-01T00:01:00Z', 's'), DT('2014-01-01T00:01Z', 'm'), True) check_eq(DT('2014-01-01T00:01:01Z', 's'), DT('2014-01-01T00:01Z', 'm'), False) # NaTs check_lt(DT('NaT', 'Y'), DT('2017'), True) check_eq(DT('NaT'), DT('NaT'), True) # Check comparison between various units dts = self.datetime_samples() for a in dts: # Take a number of smaller units a_unit = a.dtype.str.split('[')[1][:-1] i = all_units.index(a_unit) units = all_units[i:i + 6] for unit in units: # Force conversion b = a.astype('M8[%s]' % unit) if (not npdatetime_helpers.same_kind(value_unit(a), value_unit(b))): continue check_eq(a, b, True) check_lt(a, b + np.timedelta64(1, unit), True) check_lt(b - np.timedelta64(1, unit), a, True)