Construct a lazily decorated wrapper of f. The decorated function will be compiled when it is called for the first time, and it will replace its own __code__ object so subsequent calls are fast. Parameters ---------- f : callable A function to be
(self, f)
| 605 | return func |
| 606 | |
| 607 | def __call__(self, f): |
| 608 | """Construct a lazily decorated wrapper of f. |
| 609 | |
| 610 | The decorated function will be compiled when it is called for the first time, |
| 611 | and it will replace its own __code__ object so subsequent calls are fast. |
| 612 | |
| 613 | Parameters |
| 614 | ---------- |
| 615 | f : callable |
| 616 | A function to be decorated. |
| 617 | |
| 618 | Returns |
| 619 | ------- |
| 620 | func : callable |
| 621 | The decorated function. |
| 622 | |
| 623 | See Also |
| 624 | -------- |
| 625 | argmap._lazy_compile |
| 626 | """ |
| 627 | |
| 628 | if inspect.isgeneratorfunction(f): |
| 629 | |
| 630 | def func(*args, __wrapper=None, **kwargs): |
| 631 | yield from argmap._lazy_compile(__wrapper)(*args, **kwargs) |
| 632 | |
| 633 | else: |
| 634 | |
| 635 | def func(*args, __wrapper=None, **kwargs): |
| 636 | return argmap._lazy_compile(__wrapper)(*args, **kwargs) |
| 637 | |
| 638 | # standard function-wrapping stuff |
| 639 | func.__name__ = f.__name__ |
| 640 | func.__doc__ = f.__doc__ |
| 641 | func.__defaults__ = f.__defaults__ |
| 642 | func.__kwdefaults__.update(f.__kwdefaults__ or {}) |
| 643 | func.__module__ = f.__module__ |
| 644 | func.__qualname__ = f.__qualname__ |
| 645 | func.__dict__.update(f.__dict__) |
| 646 | func.__wrapped__ = f |
| 647 | |
| 648 | # now that we've wrapped f, we may have picked up some __dict__ or |
| 649 | # __kwdefaults__ items that were set by a previous argmap. Thus, we set |
| 650 | # these values after those update() calls. |
| 651 | |
| 652 | # If we attempt to access func from within itself, that happens through |
| 653 | # a closure -- which trips an error when we replace func.__code__. The |
| 654 | # standard workaround for functions which can't see themselves is to use |
| 655 | # a Y-combinator, as we do here. |
| 656 | func.__kwdefaults__["_argmap__wrapper"] = func |
| 657 | |
| 658 | # this self-reference is here because functools.wraps preserves |
| 659 | # everything in __dict__, and we don't want to mistake a non-argmap |
| 660 | # wrapper for an argmap wrapper |
| 661 | func.__self__ = func |
| 662 | |
| 663 | # this is used to variously call self.assemble and self.compile |
| 664 | func.__argmap__ = self |