Skip to content

approx with timedelta: rel parameter treated as absolute tolerance despite its name #14462

@EternalRights

Description

@EternalRights

Was playing around with the new approx datetime/timedelta support and noticed something weird about how rel works for timedelta.

For numbers, rel is a relative tolerance -- a fraction of the expected value:

approx(100, rel=0.05)  # within 5% of 100

But for timedelta, rel just acts as another absolute tolerance. It gets merged with abs via max():

approx(timedelta(seconds=100), rel=timedelta(seconds=5), abs=timedelta(seconds=2))
# tolerance = max(5s, 2s) = 5s -- not 5% of anything

The confusing part is that the parameter is called rel and the TypeError message says "relative tolerance for timedelta must be a timedelta", but the behavior is purely absolute. The relevant code in ApproxTimedelta.__init__ (around line 594):

tolerance = max(t for t in (abs, rel) if t is not None)

So rel and abs are effectively the same thing for timedelta -- whichever is larger wins. I get that multiplying two timedeltas does not work, but then maybe rel should just be rejected for timedelta the same way it is for datetime? Or accept a float and compute rel * expected (timedelta * float does work).

Not sure what the right fix is, just found this surprising when I tried using rel and realized it was not doing what I expected.

Metadata

Metadata

Assignees

No one assigned

    Labels

    topic: approxrelated to pytest.approx function

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions