Mercurial > repos > shellac > guppy_basecaller
comparison env/lib/python3.7/site-packages/dateutil/relativedelta.py @ 0:26e78fe6e8c4 draft
"planemo upload commit c699937486c35866861690329de38ec1a5d9f783"
| author | shellac |
|---|---|
| date | Sat, 02 May 2020 07:14:21 -0400 |
| parents | |
| children |
comparison
equal
deleted
inserted
replaced
| -1:000000000000 | 0:26e78fe6e8c4 |
|---|---|
| 1 # -*- coding: utf-8 -*- | |
| 2 import datetime | |
| 3 import calendar | |
| 4 | |
| 5 import operator | |
| 6 from math import copysign | |
| 7 | |
| 8 from six import integer_types | |
| 9 from warnings import warn | |
| 10 | |
| 11 from ._common import weekday | |
| 12 | |
| 13 MO, TU, WE, TH, FR, SA, SU = weekdays = tuple(weekday(x) for x in range(7)) | |
| 14 | |
| 15 __all__ = ["relativedelta", "MO", "TU", "WE", "TH", "FR", "SA", "SU"] | |
| 16 | |
| 17 | |
| 18 class relativedelta(object): | |
| 19 """ | |
| 20 The relativedelta type is designed to be applied to an existing datetime and | |
| 21 can replace specific components of that datetime, or represents an interval | |
| 22 of time. | |
| 23 | |
| 24 It is based on the specification of the excellent work done by M.-A. Lemburg | |
| 25 in his | |
| 26 `mx.DateTime <https://www.egenix.com/products/python/mxBase/mxDateTime/>`_ extension. | |
| 27 However, notice that this type does *NOT* implement the same algorithm as | |
| 28 his work. Do *NOT* expect it to behave like mx.DateTime's counterpart. | |
| 29 | |
| 30 There are two different ways to build a relativedelta instance. The | |
| 31 first one is passing it two date/datetime classes:: | |
| 32 | |
| 33 relativedelta(datetime1, datetime2) | |
| 34 | |
| 35 The second one is passing it any number of the following keyword arguments:: | |
| 36 | |
| 37 relativedelta(arg1=x,arg2=y,arg3=z...) | |
| 38 | |
| 39 year, month, day, hour, minute, second, microsecond: | |
| 40 Absolute information (argument is singular); adding or subtracting a | |
| 41 relativedelta with absolute information does not perform an arithmetic | |
| 42 operation, but rather REPLACES the corresponding value in the | |
| 43 original datetime with the value(s) in relativedelta. | |
| 44 | |
| 45 years, months, weeks, days, hours, minutes, seconds, microseconds: | |
| 46 Relative information, may be negative (argument is plural); adding | |
| 47 or subtracting a relativedelta with relative information performs | |
| 48 the corresponding arithmetic operation on the original datetime value | |
| 49 with the information in the relativedelta. | |
| 50 | |
| 51 weekday: | |
| 52 One of the weekday instances (MO, TU, etc) available in the | |
| 53 relativedelta module. These instances may receive a parameter N, | |
| 54 specifying the Nth weekday, which could be positive or negative | |
| 55 (like MO(+1) or MO(-2)). Not specifying it is the same as specifying | |
| 56 +1. You can also use an integer, where 0=MO. This argument is always | |
| 57 relative e.g. if the calculated date is already Monday, using MO(1) | |
| 58 or MO(-1) won't change the day. To effectively make it absolute, use | |
| 59 it in combination with the day argument (e.g. day=1, MO(1) for first | |
| 60 Monday of the month). | |
| 61 | |
| 62 leapdays: | |
| 63 Will add given days to the date found, if year is a leap | |
| 64 year, and the date found is post 28 of february. | |
| 65 | |
| 66 yearday, nlyearday: | |
| 67 Set the yearday or the non-leap year day (jump leap days). | |
| 68 These are converted to day/month/leapdays information. | |
| 69 | |
| 70 There are relative and absolute forms of the keyword | |
| 71 arguments. The plural is relative, and the singular is | |
| 72 absolute. For each argument in the order below, the absolute form | |
| 73 is applied first (by setting each attribute to that value) and | |
| 74 then the relative form (by adding the value to the attribute). | |
| 75 | |
| 76 The order of attributes considered when this relativedelta is | |
| 77 added to a datetime is: | |
| 78 | |
| 79 1. Year | |
| 80 2. Month | |
| 81 3. Day | |
| 82 4. Hours | |
| 83 5. Minutes | |
| 84 6. Seconds | |
| 85 7. Microseconds | |
| 86 | |
| 87 Finally, weekday is applied, using the rule described above. | |
| 88 | |
| 89 For example | |
| 90 | |
| 91 >>> from datetime import datetime | |
| 92 >>> from dateutil.relativedelta import relativedelta, MO | |
| 93 >>> dt = datetime(2018, 4, 9, 13, 37, 0) | |
| 94 >>> delta = relativedelta(hours=25, day=1, weekday=MO(1)) | |
| 95 >>> dt + delta | |
| 96 datetime.datetime(2018, 4, 2, 14, 37) | |
| 97 | |
| 98 First, the day is set to 1 (the first of the month), then 25 hours | |
| 99 are added, to get to the 2nd day and 14th hour, finally the | |
| 100 weekday is applied, but since the 2nd is already a Monday there is | |
| 101 no effect. | |
| 102 | |
| 103 """ | |
| 104 | |
| 105 def __init__(self, dt1=None, dt2=None, | |
| 106 years=0, months=0, days=0, leapdays=0, weeks=0, | |
| 107 hours=0, minutes=0, seconds=0, microseconds=0, | |
| 108 year=None, month=None, day=None, weekday=None, | |
| 109 yearday=None, nlyearday=None, | |
| 110 hour=None, minute=None, second=None, microsecond=None): | |
| 111 | |
| 112 if dt1 and dt2: | |
| 113 # datetime is a subclass of date. So both must be date | |
| 114 if not (isinstance(dt1, datetime.date) and | |
| 115 isinstance(dt2, datetime.date)): | |
| 116 raise TypeError("relativedelta only diffs datetime/date") | |
| 117 | |
| 118 # We allow two dates, or two datetimes, so we coerce them to be | |
| 119 # of the same type | |
| 120 if (isinstance(dt1, datetime.datetime) != | |
| 121 isinstance(dt2, datetime.datetime)): | |
| 122 if not isinstance(dt1, datetime.datetime): | |
| 123 dt1 = datetime.datetime.fromordinal(dt1.toordinal()) | |
| 124 elif not isinstance(dt2, datetime.datetime): | |
| 125 dt2 = datetime.datetime.fromordinal(dt2.toordinal()) | |
| 126 | |
| 127 self.years = 0 | |
| 128 self.months = 0 | |
| 129 self.days = 0 | |
| 130 self.leapdays = 0 | |
| 131 self.hours = 0 | |
| 132 self.minutes = 0 | |
| 133 self.seconds = 0 | |
| 134 self.microseconds = 0 | |
| 135 self.year = None | |
| 136 self.month = None | |
| 137 self.day = None | |
| 138 self.weekday = None | |
| 139 self.hour = None | |
| 140 self.minute = None | |
| 141 self.second = None | |
| 142 self.microsecond = None | |
| 143 self._has_time = 0 | |
| 144 | |
| 145 # Get year / month delta between the two | |
| 146 months = (dt1.year - dt2.year) * 12 + (dt1.month - dt2.month) | |
| 147 self._set_months(months) | |
| 148 | |
| 149 # Remove the year/month delta so the timedelta is just well-defined | |
| 150 # time units (seconds, days and microseconds) | |
| 151 dtm = self.__radd__(dt2) | |
| 152 | |
| 153 # If we've overshot our target, make an adjustment | |
| 154 if dt1 < dt2: | |
| 155 compare = operator.gt | |
| 156 increment = 1 | |
| 157 else: | |
| 158 compare = operator.lt | |
| 159 increment = -1 | |
| 160 | |
| 161 while compare(dt1, dtm): | |
| 162 months += increment | |
| 163 self._set_months(months) | |
| 164 dtm = self.__radd__(dt2) | |
| 165 | |
| 166 # Get the timedelta between the "months-adjusted" date and dt1 | |
| 167 delta = dt1 - dtm | |
| 168 self.seconds = delta.seconds + delta.days * 86400 | |
| 169 self.microseconds = delta.microseconds | |
| 170 else: | |
| 171 # Check for non-integer values in integer-only quantities | |
| 172 if any(x is not None and x != int(x) for x in (years, months)): | |
| 173 raise ValueError("Non-integer years and months are " | |
| 174 "ambiguous and not currently supported.") | |
| 175 | |
| 176 # Relative information | |
| 177 self.years = int(years) | |
| 178 self.months = int(months) | |
| 179 self.days = days + weeks * 7 | |
| 180 self.leapdays = leapdays | |
| 181 self.hours = hours | |
| 182 self.minutes = minutes | |
| 183 self.seconds = seconds | |
| 184 self.microseconds = microseconds | |
| 185 | |
| 186 # Absolute information | |
| 187 self.year = year | |
| 188 self.month = month | |
| 189 self.day = day | |
| 190 self.hour = hour | |
| 191 self.minute = minute | |
| 192 self.second = second | |
| 193 self.microsecond = microsecond | |
| 194 | |
| 195 if any(x is not None and int(x) != x | |
| 196 for x in (year, month, day, hour, | |
| 197 minute, second, microsecond)): | |
| 198 # For now we'll deprecate floats - later it'll be an error. | |
| 199 warn("Non-integer value passed as absolute information. " + | |
| 200 "This is not a well-defined condition and will raise " + | |
| 201 "errors in future versions.", DeprecationWarning) | |
| 202 | |
| 203 if isinstance(weekday, integer_types): | |
| 204 self.weekday = weekdays[weekday] | |
| 205 else: | |
| 206 self.weekday = weekday | |
| 207 | |
| 208 yday = 0 | |
| 209 if nlyearday: | |
| 210 yday = nlyearday | |
| 211 elif yearday: | |
| 212 yday = yearday | |
| 213 if yearday > 59: | |
| 214 self.leapdays = -1 | |
| 215 if yday: | |
| 216 ydayidx = [31, 59, 90, 120, 151, 181, 212, | |
| 217 243, 273, 304, 334, 366] | |
| 218 for idx, ydays in enumerate(ydayidx): | |
| 219 if yday <= ydays: | |
| 220 self.month = idx+1 | |
| 221 if idx == 0: | |
| 222 self.day = yday | |
| 223 else: | |
| 224 self.day = yday-ydayidx[idx-1] | |
| 225 break | |
| 226 else: | |
| 227 raise ValueError("invalid year day (%d)" % yday) | |
| 228 | |
| 229 self._fix() | |
| 230 | |
| 231 def _fix(self): | |
| 232 if abs(self.microseconds) > 999999: | |
| 233 s = _sign(self.microseconds) | |
| 234 div, mod = divmod(self.microseconds * s, 1000000) | |
| 235 self.microseconds = mod * s | |
| 236 self.seconds += div * s | |
| 237 if abs(self.seconds) > 59: | |
| 238 s = _sign(self.seconds) | |
| 239 div, mod = divmod(self.seconds * s, 60) | |
| 240 self.seconds = mod * s | |
| 241 self.minutes += div * s | |
| 242 if abs(self.minutes) > 59: | |
| 243 s = _sign(self.minutes) | |
| 244 div, mod = divmod(self.minutes * s, 60) | |
| 245 self.minutes = mod * s | |
| 246 self.hours += div * s | |
| 247 if abs(self.hours) > 23: | |
| 248 s = _sign(self.hours) | |
| 249 div, mod = divmod(self.hours * s, 24) | |
| 250 self.hours = mod * s | |
| 251 self.days += div * s | |
| 252 if abs(self.months) > 11: | |
| 253 s = _sign(self.months) | |
| 254 div, mod = divmod(self.months * s, 12) | |
| 255 self.months = mod * s | |
| 256 self.years += div * s | |
| 257 if (self.hours or self.minutes or self.seconds or self.microseconds | |
| 258 or self.hour is not None or self.minute is not None or | |
| 259 self.second is not None or self.microsecond is not None): | |
| 260 self._has_time = 1 | |
| 261 else: | |
| 262 self._has_time = 0 | |
| 263 | |
| 264 @property | |
| 265 def weeks(self): | |
| 266 return int(self.days / 7.0) | |
| 267 | |
| 268 @weeks.setter | |
| 269 def weeks(self, value): | |
| 270 self.days = self.days - (self.weeks * 7) + value * 7 | |
| 271 | |
| 272 def _set_months(self, months): | |
| 273 self.months = months | |
| 274 if abs(self.months) > 11: | |
| 275 s = _sign(self.months) | |
| 276 div, mod = divmod(self.months * s, 12) | |
| 277 self.months = mod * s | |
| 278 self.years = div * s | |
| 279 else: | |
| 280 self.years = 0 | |
| 281 | |
| 282 def normalized(self): | |
| 283 """ | |
| 284 Return a version of this object represented entirely using integer | |
| 285 values for the relative attributes. | |
| 286 | |
| 287 >>> relativedelta(days=1.5, hours=2).normalized() | |
| 288 relativedelta(days=+1, hours=+14) | |
| 289 | |
| 290 :return: | |
| 291 Returns a :class:`dateutil.relativedelta.relativedelta` object. | |
| 292 """ | |
| 293 # Cascade remainders down (rounding each to roughly nearest microsecond) | |
| 294 days = int(self.days) | |
| 295 | |
| 296 hours_f = round(self.hours + 24 * (self.days - days), 11) | |
| 297 hours = int(hours_f) | |
| 298 | |
| 299 minutes_f = round(self.minutes + 60 * (hours_f - hours), 10) | |
| 300 minutes = int(minutes_f) | |
| 301 | |
| 302 seconds_f = round(self.seconds + 60 * (minutes_f - minutes), 8) | |
| 303 seconds = int(seconds_f) | |
| 304 | |
| 305 microseconds = round(self.microseconds + 1e6 * (seconds_f - seconds)) | |
| 306 | |
| 307 # Constructor carries overflow back up with call to _fix() | |
| 308 return self.__class__(years=self.years, months=self.months, | |
| 309 days=days, hours=hours, minutes=minutes, | |
| 310 seconds=seconds, microseconds=microseconds, | |
| 311 leapdays=self.leapdays, year=self.year, | |
| 312 month=self.month, day=self.day, | |
| 313 weekday=self.weekday, hour=self.hour, | |
| 314 minute=self.minute, second=self.second, | |
| 315 microsecond=self.microsecond) | |
| 316 | |
| 317 def __add__(self, other): | |
| 318 if isinstance(other, relativedelta): | |
| 319 return self.__class__(years=other.years + self.years, | |
| 320 months=other.months + self.months, | |
| 321 days=other.days + self.days, | |
| 322 hours=other.hours + self.hours, | |
| 323 minutes=other.minutes + self.minutes, | |
| 324 seconds=other.seconds + self.seconds, | |
| 325 microseconds=(other.microseconds + | |
| 326 self.microseconds), | |
| 327 leapdays=other.leapdays or self.leapdays, | |
| 328 year=(other.year if other.year is not None | |
| 329 else self.year), | |
| 330 month=(other.month if other.month is not None | |
| 331 else self.month), | |
| 332 day=(other.day if other.day is not None | |
| 333 else self.day), | |
| 334 weekday=(other.weekday if other.weekday is not None | |
| 335 else self.weekday), | |
| 336 hour=(other.hour if other.hour is not None | |
| 337 else self.hour), | |
| 338 minute=(other.minute if other.minute is not None | |
| 339 else self.minute), | |
| 340 second=(other.second if other.second is not None | |
| 341 else self.second), | |
| 342 microsecond=(other.microsecond if other.microsecond | |
| 343 is not None else | |
| 344 self.microsecond)) | |
| 345 if isinstance(other, datetime.timedelta): | |
| 346 return self.__class__(years=self.years, | |
| 347 months=self.months, | |
| 348 days=self.days + other.days, | |
| 349 hours=self.hours, | |
| 350 minutes=self.minutes, | |
| 351 seconds=self.seconds + other.seconds, | |
| 352 microseconds=self.microseconds + other.microseconds, | |
| 353 leapdays=self.leapdays, | |
| 354 year=self.year, | |
| 355 month=self.month, | |
| 356 day=self.day, | |
| 357 weekday=self.weekday, | |
| 358 hour=self.hour, | |
| 359 minute=self.minute, | |
| 360 second=self.second, | |
| 361 microsecond=self.microsecond) | |
| 362 if not isinstance(other, datetime.date): | |
| 363 return NotImplemented | |
| 364 elif self._has_time and not isinstance(other, datetime.datetime): | |
| 365 other = datetime.datetime.fromordinal(other.toordinal()) | |
| 366 year = (self.year or other.year)+self.years | |
| 367 month = self.month or other.month | |
| 368 if self.months: | |
| 369 assert 1 <= abs(self.months) <= 12 | |
| 370 month += self.months | |
| 371 if month > 12: | |
| 372 year += 1 | |
| 373 month -= 12 | |
| 374 elif month < 1: | |
| 375 year -= 1 | |
| 376 month += 12 | |
| 377 day = min(calendar.monthrange(year, month)[1], | |
| 378 self.day or other.day) | |
| 379 repl = {"year": year, "month": month, "day": day} | |
| 380 for attr in ["hour", "minute", "second", "microsecond"]: | |
| 381 value = getattr(self, attr) | |
| 382 if value is not None: | |
| 383 repl[attr] = value | |
| 384 days = self.days | |
| 385 if self.leapdays and month > 2 and calendar.isleap(year): | |
| 386 days += self.leapdays | |
| 387 ret = (other.replace(**repl) | |
| 388 + datetime.timedelta(days=days, | |
| 389 hours=self.hours, | |
| 390 minutes=self.minutes, | |
| 391 seconds=self.seconds, | |
| 392 microseconds=self.microseconds)) | |
| 393 if self.weekday: | |
| 394 weekday, nth = self.weekday.weekday, self.weekday.n or 1 | |
| 395 jumpdays = (abs(nth) - 1) * 7 | |
| 396 if nth > 0: | |
| 397 jumpdays += (7 - ret.weekday() + weekday) % 7 | |
| 398 else: | |
| 399 jumpdays += (ret.weekday() - weekday) % 7 | |
| 400 jumpdays *= -1 | |
| 401 ret += datetime.timedelta(days=jumpdays) | |
| 402 return ret | |
| 403 | |
| 404 def __radd__(self, other): | |
| 405 return self.__add__(other) | |
| 406 | |
| 407 def __rsub__(self, other): | |
| 408 return self.__neg__().__radd__(other) | |
| 409 | |
| 410 def __sub__(self, other): | |
| 411 if not isinstance(other, relativedelta): | |
| 412 return NotImplemented # In case the other object defines __rsub__ | |
| 413 return self.__class__(years=self.years - other.years, | |
| 414 months=self.months - other.months, | |
| 415 days=self.days - other.days, | |
| 416 hours=self.hours - other.hours, | |
| 417 minutes=self.minutes - other.minutes, | |
| 418 seconds=self.seconds - other.seconds, | |
| 419 microseconds=self.microseconds - other.microseconds, | |
| 420 leapdays=self.leapdays or other.leapdays, | |
| 421 year=(self.year if self.year is not None | |
| 422 else other.year), | |
| 423 month=(self.month if self.month is not None else | |
| 424 other.month), | |
| 425 day=(self.day if self.day is not None else | |
| 426 other.day), | |
| 427 weekday=(self.weekday if self.weekday is not None else | |
| 428 other.weekday), | |
| 429 hour=(self.hour if self.hour is not None else | |
| 430 other.hour), | |
| 431 minute=(self.minute if self.minute is not None else | |
| 432 other.minute), | |
| 433 second=(self.second if self.second is not None else | |
| 434 other.second), | |
| 435 microsecond=(self.microsecond if self.microsecond | |
| 436 is not None else | |
| 437 other.microsecond)) | |
| 438 | |
| 439 def __abs__(self): | |
| 440 return self.__class__(years=abs(self.years), | |
| 441 months=abs(self.months), | |
| 442 days=abs(self.days), | |
| 443 hours=abs(self.hours), | |
| 444 minutes=abs(self.minutes), | |
| 445 seconds=abs(self.seconds), | |
| 446 microseconds=abs(self.microseconds), | |
| 447 leapdays=self.leapdays, | |
| 448 year=self.year, | |
| 449 month=self.month, | |
| 450 day=self.day, | |
| 451 weekday=self.weekday, | |
| 452 hour=self.hour, | |
| 453 minute=self.minute, | |
| 454 second=self.second, | |
| 455 microsecond=self.microsecond) | |
| 456 | |
| 457 def __neg__(self): | |
| 458 return self.__class__(years=-self.years, | |
| 459 months=-self.months, | |
| 460 days=-self.days, | |
| 461 hours=-self.hours, | |
| 462 minutes=-self.minutes, | |
| 463 seconds=-self.seconds, | |
| 464 microseconds=-self.microseconds, | |
| 465 leapdays=self.leapdays, | |
| 466 year=self.year, | |
| 467 month=self.month, | |
| 468 day=self.day, | |
| 469 weekday=self.weekday, | |
| 470 hour=self.hour, | |
| 471 minute=self.minute, | |
| 472 second=self.second, | |
| 473 microsecond=self.microsecond) | |
| 474 | |
| 475 def __bool__(self): | |
| 476 return not (not self.years and | |
| 477 not self.months and | |
| 478 not self.days and | |
| 479 not self.hours and | |
| 480 not self.minutes and | |
| 481 not self.seconds and | |
| 482 not self.microseconds and | |
| 483 not self.leapdays and | |
| 484 self.year is None and | |
| 485 self.month is None and | |
| 486 self.day is None and | |
| 487 self.weekday is None and | |
| 488 self.hour is None and | |
| 489 self.minute is None and | |
| 490 self.second is None and | |
| 491 self.microsecond is None) | |
| 492 # Compatibility with Python 2.x | |
| 493 __nonzero__ = __bool__ | |
| 494 | |
| 495 def __mul__(self, other): | |
| 496 try: | |
| 497 f = float(other) | |
| 498 except TypeError: | |
| 499 return NotImplemented | |
| 500 | |
| 501 return self.__class__(years=int(self.years * f), | |
| 502 months=int(self.months * f), | |
| 503 days=int(self.days * f), | |
| 504 hours=int(self.hours * f), | |
| 505 minutes=int(self.minutes * f), | |
| 506 seconds=int(self.seconds * f), | |
| 507 microseconds=int(self.microseconds * f), | |
| 508 leapdays=self.leapdays, | |
| 509 year=self.year, | |
| 510 month=self.month, | |
| 511 day=self.day, | |
| 512 weekday=self.weekday, | |
| 513 hour=self.hour, | |
| 514 minute=self.minute, | |
| 515 second=self.second, | |
| 516 microsecond=self.microsecond) | |
| 517 | |
| 518 __rmul__ = __mul__ | |
| 519 | |
| 520 def __eq__(self, other): | |
| 521 if not isinstance(other, relativedelta): | |
| 522 return NotImplemented | |
| 523 if self.weekday or other.weekday: | |
| 524 if not self.weekday or not other.weekday: | |
| 525 return False | |
| 526 if self.weekday.weekday != other.weekday.weekday: | |
| 527 return False | |
| 528 n1, n2 = self.weekday.n, other.weekday.n | |
| 529 if n1 != n2 and not ((not n1 or n1 == 1) and (not n2 or n2 == 1)): | |
| 530 return False | |
| 531 return (self.years == other.years and | |
| 532 self.months == other.months and | |
| 533 self.days == other.days and | |
| 534 self.hours == other.hours and | |
| 535 self.minutes == other.minutes and | |
| 536 self.seconds == other.seconds and | |
| 537 self.microseconds == other.microseconds and | |
| 538 self.leapdays == other.leapdays and | |
| 539 self.year == other.year and | |
| 540 self.month == other.month and | |
| 541 self.day == other.day and | |
| 542 self.hour == other.hour and | |
| 543 self.minute == other.minute and | |
| 544 self.second == other.second and | |
| 545 self.microsecond == other.microsecond) | |
| 546 | |
| 547 def __hash__(self): | |
| 548 return hash(( | |
| 549 self.weekday, | |
| 550 self.years, | |
| 551 self.months, | |
| 552 self.days, | |
| 553 self.hours, | |
| 554 self.minutes, | |
| 555 self.seconds, | |
| 556 self.microseconds, | |
| 557 self.leapdays, | |
| 558 self.year, | |
| 559 self.month, | |
| 560 self.day, | |
| 561 self.hour, | |
| 562 self.minute, | |
| 563 self.second, | |
| 564 self.microsecond, | |
| 565 )) | |
| 566 | |
| 567 def __ne__(self, other): | |
| 568 return not self.__eq__(other) | |
| 569 | |
| 570 def __div__(self, other): | |
| 571 try: | |
| 572 reciprocal = 1 / float(other) | |
| 573 except TypeError: | |
| 574 return NotImplemented | |
| 575 | |
| 576 return self.__mul__(reciprocal) | |
| 577 | |
| 578 __truediv__ = __div__ | |
| 579 | |
| 580 def __repr__(self): | |
| 581 l = [] | |
| 582 for attr in ["years", "months", "days", "leapdays", | |
| 583 "hours", "minutes", "seconds", "microseconds"]: | |
| 584 value = getattr(self, attr) | |
| 585 if value: | |
| 586 l.append("{attr}={value:+g}".format(attr=attr, value=value)) | |
| 587 for attr in ["year", "month", "day", "weekday", | |
| 588 "hour", "minute", "second", "microsecond"]: | |
| 589 value = getattr(self, attr) | |
| 590 if value is not None: | |
| 591 l.append("{attr}={value}".format(attr=attr, value=repr(value))) | |
| 592 return "{classname}({attrs})".format(classname=self.__class__.__name__, | |
| 593 attrs=", ".join(l)) | |
| 594 | |
| 595 | |
| 596 def _sign(x): | |
| 597 return int(copysign(1, x)) | |
| 598 | |
| 599 # vim:ts=4:sw=4:et |
