FazBrowse GitHub Viewer | Trending |
URL:
| Home
Tools: [Download Repo ZIP]   [Original HTTPS Page]

gh-131798: constant fold classmethod and staticmethod in JIT by kumaraditya303 · Pull Request #148331 · python/cpython · GitHub

Repository navigation

gh-131798: constant fold classmethod and staticmethod in JIT - #148331

Closed
kumaraditya303 wants to merge 7 commits into
python:mainfrom
kumaraditya303:jit-classmethod
Closed

kumaraditya303 wants to merge 7 commits into
python:mainfrom
kumaraditya303:jit-classmethod

Conversation

kumaraditya303 commented Apr 10, 2026 •
edited
Loading

Copy link
Copy Markdown
Contributor

Script used for benchmark:

"""Benchmark for classmethod/staticmethod JIT optimization."""

import time

LOOPS = 10_000_000


class MyClass:
    @classmethod
    def class_method(cls):
        return cls

    @staticmethod
    def static_method():
        return 42

    def regular_method(self):
        return self


obj = MyClass()


def bench_classmethod():
    o = obj
    for _ in range(LOOPS):
        o.class_method()
        o.class_method()
        o.class_method()
        o.class_method()
        o.class_method()


def bench_staticmethod():
    o = obj
    for _ in range(LOOPS):
        o.static_method()
        o.static_method()
        o.static_method()
        o.static_method()
        o.static_method()


benchmarks = [
    ("classmethod", bench_classmethod),
    ("staticmethod", bench_staticmethod),
]

for name, func in benchmarks:
    t0 = time.perf_counter()
    func()
    dt = time.perf_counter() - t0
    print(f"{name:20s} {dt:.3f}s")
Benchmark main PR Speedup
classmethod 1.000s 0.572s 1.75x faster
staticmethod 0.860s 0.482s 1.78x faster

Copy link
Copy Markdown
Contributor Author

This can be done for class lookups as well so things like Foo.bar() where bar is a classmethod gets constant folded.

Copy link
Copy Markdown
Member

I don't see any change in deltablue, but that's because it's using cls.classmethod() instead of self.classmethod(). Would you like to add that to this PR as well? https://github.com/python/pyperformance/blob/main/pyperformance/data-files/benchmarks/bm_deltablue/run_benchmark.py#L234

Copy link
Copy Markdown
Member

I don't see any change in deltablue, but that's because it's using cls.classmethod() instead of self.classmethod(). Would you like to add that to this PR as well? https://github.com/python/pyperformance/blob/main/pyperformance/data-files/benchmarks/bm_deltablue/run_benchmark.py#L234

This turned out to be harder than I thought, because it would fold the classmethod descriptor into a unbound method lookup rather than a bound one, which changes the following CALL_BOUND_METHOD_EXACT_ARGS in the trace.

Copy link
Copy Markdown
Member

The outer else doesn't set self_or_null[0], intentional?

Comment thread Python/optimizer_bytecodes.c Outdated

Copy link
Copy Markdown
Member

I don't see any change in deltablue, but that's because it's using cls.classmethod() instead of self.classmethod(). Would you like to add that to this PR as well? https://github.com/python/pyperformance/blob/main/pyperformance/data-files/benchmarks/bm_deltablue/run_benchmark.py#L234

This turned out to be harder than I thought, because it would fold the classmethod descriptor into a unbound method lookup rather than a bound one, which changes the following CALL_BOUND_METHOD_EXACT_ARGS in the trace.

That shouldn't be a problem for staticmethod though, as self_or_null is always NULL.

It would make sense for LOAD_ATTR 1 for classmethod to be leaving func cls on the stack.

If we special case classmethod in _PyObject_GetMethodStackRef, it should add negligible overhead in the interpreter (possibly speeding things up if classmethods are common) and will enable this optimization in the JIT.

Copy link
Copy Markdown
Member

If we special case classmethod in _PyObject_GetMethodStackRef, it should add negligible overhead in the interpreter (possibly speeding things up if classmethods are common) and will enable this optimization in the JIT.

Working on that.

Copy link
Copy Markdown

This PR is stale because it has been open for 30 days with no activity.

github-actions Bot added the stale Stale PR or inactive for long period of time. label May 18, 2026

ambv commented Oct 20, 2026

Copy link
Copy Markdown
Contributor

This PR is superseded by #157011, a newer open pull request for the same issue (gh-131798), and it no longer merges cleanly. Closing to cull the number of open pull requests. Do not reopen this pull request without getting a go-ahead from a triager or core developer.

ambv closed this Oct 20, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode characters
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

awaiting core review skip news stale Stale PR or inactive for long period of time. topic-JIT

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants


Back | FazBrowse Home | New Git URL