You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Upon construction, all Time objects contain two double-precision values, jd1 and jd2. These satisfy, and are tested to satisfy, the invariant that jd1 is an integer, abs(jd2)<=0.5, and if abs(jd2)==0.5 then jd1 is even. This is enforced by application of the not-publicly-documented function day_frac.
When a Time object is converted from one timescale to another, though, under some circumstances abs(jd2)>0.5.
Fixing this is a little bit subtle because during conversion new Time objects are constructed with from_jd=True, in which case almost no validation is done, and existing tests check whether the original arrays remain untouched. So any time from_jd is True is an opportunity for the constructed objects to violate Time invariants, though the custom format validation code has caught some cases. The idea is, I think, that from_jd=True construction should be internal and efficient and maybe involve already-converted data.
Alternatively one could track down where (non-custom) scale conversion is done and fix that so that it always maintained the invariant. That won't prevent users from creating silently non-conformant Time objects with badly implemented custom scales. Most code probably doesn't actually care whether jd1 is an integer or half-integer, but some certainly does, and that code will break.
Nice find. Indeed, a missing day_frac call after the scale change. Note that I don't think we ever promised the fraction would always be <=0.5, though we've certainly made efforts to ensure it does on input. For precision purposes, it may not help much - one bit of precision has already been lost by the erfa routine. But it may make sense to try to make this more of a promise and thus to fix this.
Activity
pllim commentedon Nov 5, 2019
cc @mhvk and @taldcroft
aarchiba commentedon Nov 5, 2019
Fixing this is a little bit subtle because during conversion new Time objects are constructed with
from_jd=True, in which case almost no validation is done, and existing tests check whether the original arrays remain untouched. So any timefrom_jdisTrueis an opportunity for the constructed objects to violateTimeinvariants, though the custom format validation code has caught some cases. The idea is, I think, thatfrom_jd=Trueconstruction should be internal and efficient and maybe involve already-converted data.Alternatively one could track down where (non-custom) scale conversion is done and fix that so that it always maintained the invariant. That won't prevent users from creating silently non-conformant Time objects with badly implemented custom scales. Most code probably doesn't actually care whether
jd1is an integer or half-integer, but some certainly does, and that code will break.mhvk commentedon Nov 5, 2019
Nice find. Indeed, a missing
day_fraccall after the scale change. Note that I don't think we ever promised the fraction would always be <=0.5, though we've certainly made efforts to ensure it does on input. For precision purposes, it may not help much - one bit of precision has already been lost by the erfa routine. But it may make sense to try to make this more of a promise and thus to fix this.aarchiba commentedon Nov 8, 2019
Now fixed in #9532 ; it's a one-line fix. I didn't add general validation, so custom formats can still make jd2>jd1 (for example).
pllim commentedon Nov 8, 2019
@aarchiba , given that #9532 might be open for a while yet, is it possible for you to submit the one-liner bug fix as its own PR? Thanks!
Fix astropy#9533
Fix astropy#9533