You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python中如何在静态方法内部获取自身的限定名__qualname__

解决方案

推荐两种实现方案,按你的场景适配即可:

方案1:装饰器方案(灵活可控)

直接在静态方法上挂载装饰器,定义阶段就提前获取__qualname__存好,运行时无需查栈,效率最高。
代码实现:

from functools import wraps

def auto_gen_command(func):
    # 定义阶段直接获取完整限定名
    qual_name = func.__qualname__
    @wraps(func)
    def wrapper(*args, **kwargs):
        # 可保留原函数的业务逻辑
        func(*args, **kwargs)
        # 按规则生成命令
        output_path = kwargs.get("output_path") if kwargs else args[0] if args else ""
        return f"/{qual_name.replace('.', '/')}/ {output_path}"
    return wrapper

使用方式:

class file:
    class export:
        @staticmethod
        @auto_gen_command
        def ascii(output_path):
            # 原有业务逻辑写在这里,无需再手动拼接命令字符串
            pass

测试效果:

print(file.export.ascii("test/output.txt"))
# 输出:/file/export/ascii/ test/output.txt

方案2:元类方案(批量自动适配)

如果你有数百个这类静态方法,不想逐个加装饰器,可以用元类自动扫描所有嵌套类的静态方法,批量注入逻辑,完全不用修改原有方法代码。
代码实现:

from functools import wraps
import inspect

class CommandClassMeta(type):
    def __new__(cls, name, bases, attrs):
        # 遍历当前类的所有属性
        for attr_name, attr_val in attrs.items():
            # 处理静态方法
            if isinstance(attr_val, staticmethod):
                raw_func = attr_val.__func__
                qual_name = raw_func.__qualname__
                @wraps(raw_func)
                def wrapper(*args, **kwargs):
                    raw_func(*args, **kwargs)
                    output_path = kwargs.get("output_path") if kwargs else args[0] if args else ""
                    return f"/{qual_name.replace('.', '/')}/ {output_path}"
                attrs[attr_name] = staticmethod(wrapper)
            # 递归处理嵌套类
            elif inspect.isclass(attr_val):
                attrs[attr_val.__name__] = CommandClassMeta(
                    attr_val.__name__,
                    attr_val.__bases__,
                    dict(attr_val.__dict__)
                )
        return super().__new__(cls, name, bases, attrs)

使用方式:

# 仅需给最外层的根类指定元类即可,所有嵌套类的静态方法自动适配
class file(metaclass=CommandClassMeta):
    class export:
        @staticmethod
        def ascii(output_path):
            # 原有代码完全不用改
            pass
    
    class import:
        @staticmethod
        def csv(input_path):
            # 新增方法也不用加额外装饰器
            pass

测试效果:

print(file.import.csv("data/input.csv"))
# 输出:/file/import/csv/ data/input.csv

不推荐方案:运行时栈查询

如果一定要在方法内部实时获取,也可以通过栈反射实现,但效率低、重名函数会出错,仅做参考:

import inspect
import sys

def get_func_qualname():
    caller_frame = inspect.currentframe().f_back
    func_name = caller_frame.f_code.co_name
    module = sys.modules[caller_frame.f_globals["__name__"]]
    # 递归遍历模块下所有类查找匹配的静态方法
    def scan_class(cls):
        for attr_name, attr_val in cls.__dict__.items():
            if isinstance(attr_val, staticmethod) and attr_val.__func__.__name__ == func_name:
                return attr_val.__func__.__qualname__
            if inspect.isclass(attr_val):
                res = scan_class(attr_val)
                if res:
                    return res
        return None
    for _, obj in inspect.getmembers(module, inspect.isclass):
        res = scan_class(obj)
        if res:
            return res
    return func_name

使用时在静态方法内调用qualname = get_func_qualname()即可。


内容的提问来源于stack exchange,提问作者Alwin

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.27 01:36:05