在Python中,在运行时确定对象是否是类(旧类型和新类型)实例

2023-11-21

我正在尝试使用 h5py 模块将一组深度嵌套的类、属性、绑定方法等写入 HDF5 文件以进行长期存储。我真的很接近。我似乎无法解决的唯一问题是在运行时以编程方式找出一种方法来确定某物是否是类实例类型,而不是列表、int 等。我需要递归到类实例,但显然不应该递归为 int、float 等。这需要适用于旧式和新式类。我研究过的东西不起作用/我无法开始工作:

使用检查模块

>>> class R(object): pass
...
>>> _R = R()
>>> import inspect
>>> inspect.isclass(_R)
False
>>> inspect.isclass(R)
True

这没有帮助,我需要一个像inspect.isclassinstance(_R)回来True

使用类型模块

如果您使用旧式类,则有一种名为 InstanceType 的类型可以匹配旧式类的实例,如下面的代码所示

>>> import types
>>> class R(): pass #old-style class
...
>>> _R = R()
>>> import types
>>> type(_R) is types.InstanceType
True
>>> class R(object): pass #new-style class
...
>>> _R = R()
>>> type(_R) is types.InstanceType
False

但是如果你使用新式类则没有对应的类型types


虽然发帖者很可能需要重新考虑他的设计,但在某些情况下,确实需要区分用 C 创建的内置/扩展类型的实例和用 Python 创建的类的实例class陈述。虽然两者都是类型,但后者是 CPython 内部称为“堆类型”的类型类别,因为它们的类型结构是在运行时分配的。 python继续区分它们可以在__repr__ output:

>>> int       # "type"
<type 'int'>
>>> class X(object): pass
... 
>>> X         # "class"
<class '__main__.X'>

The __repr__区分是通过检查类型是否是堆类型来实现的。

根据应用程序的具体需求,is_class_instance功能可以通过以下方式之一实现:

# Built-in types such as int or object do not have __dict__ by
# default. __dict__ is normally obtained by inheriting from a
# dictless type using the class statement.  Checking for the
# existence of __dict__ is an indication of a class instance.
#
# Caveat: a built-in or extension type can still request instance
# dicts using tp_dictoffset, and a class can suppress it with
# __slots__.
def is_class_instance(o):
    return hasattr(o, '__dict__')

# A reliable approach, but one that is also more dependent
# on the CPython implementation.
Py_TPFLAGS_HEAPTYPE = (1<<9)       # Include/object.h
def is_class_instance(o):
    return bool(type(o).__flags__ & Py_TPFLAGS_HEAPTYPE)

EDIT

这是该函数第二个版本的解释。它确实使用 CPython 内部出于其自身目的使用的相同测试来测试该类型是否为“堆类型”。这确保了它对于堆类型(“类”)的实例始终返回 True,对于非堆类型(“类型”,但也很容易修复的旧式类)实例始终返回 False。它通过检查是否tp_flags memberC级的PyTypeObject结构Py_TPFLAGS_HEAPTYPE位设置。该实现的薄弱部分是它硬编码了Py_TPFLAGS_HEAPTYPE恒定为当前观察到的值。 (这是必要的,因为该常量不会通过符号名称暴露给 Python。)虽然理论上该常量可能会更改,但在实践中极不可能发生,因为这种更改会无缘无故地破坏现有扩展模块的 ABI。看着的定义Py_TPFLAGS常量 in Include/object.h,很明显,新的内容正在被小心地添加,而不会干扰旧的内容。另一个弱点是此代码在非 CPython 实现(例如 Jython 或 IronPython)上运行的机会为零。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

在Python中,在运行时确定对象是否是类(旧类型和新类型)实例 的相关文章

  • tensorflow Protobuf编译问题

    我想为 google 对象检测 API 编译 protobuf 库 我按照官方教程输入protoc object detection protos proto python out 然后我得到的是 object detection prot
  • 只使用 Django 的某些部分?

    我喜欢 Django 但对于一个特定的应用程序 我只想使用它的一部分 但我对 Django 的内部工作原理还不够熟悉 所以也许有人可以指出我必须做什么的正确方向查看 具体来说 我想使用 模型和数据库抽象 The 缓存API http doc
  • 重新索引错误没有意义

    I have DataFrames大小在 100k 到 2m 之间 我正在处理这个问题的框架是如此之大 但请注意 我必须对其他框架执行相同的操作 gt gt gt len data 357451 现在这个文件是通过编译许多文件创建的 所以它
  • scipy.misc.imshow RuntimeError('无法执行图像视图')

    我正在测试scipy misc imshow https docs scipy org doc scipy 0 15 1 reference generated scipy misc imshow html我得到了运行时错误 无法执行图像查
  • Python grpc protobuf 存根生成问题:--grpc_out: protoc-gen-grpc: 插件失败,状态代码 1

    正如问题所说 我从源代码编译了 grpc 并且也做了sudo pip install grpcio 但是 那which grpc python plugin不返回任何内容 这是一个问题 因为route guide的grpc python示例
  • 我应该为 MySQL 使用什么 python 3 库? [关闭]

    Closed 此问题正在寻求书籍 工具 软件库等的推荐 不满足堆栈溢出指南 help closed questions 目前不接受答案 据我所知 MySQLdb 仍然没有移植到 Python 3 pypy 上似乎有另一个名为 PyMySQL
  • 如何为 C 分配的 numpy 数组注册析构函数?

    我想在 C C 中为 numpy 数组分配数字 并将它们作为 numpy 数组传递给 python 我可以做的PyArray SimpleNewFromData http docs scipy org doc numpy reference
  • 类型错误:需要 Future 或协程

    我尝试在 asyncssh 上自动重新连接 ssh 客户端 SshConnectManager 必须留在后台并在需要时进行 ssh 会话 class SshConnectManager object def init self host u
  • 读取文件特定行号的有效方法。 (奖励:Python 手册印刷错误)

    我有一个 100 GB 的文本文件 它是来自数据库的 BCP 转储 当我尝试导入它时BULK INSERT 我在第 219506324 行上收到一个神秘错误 在解决此问题之前 我想看看这一行 但可惜的是我最喜欢的方法 import line
  • 是否有更矢量化的方法来沿轴执行 numpy.outer ?

    gt gt gt x np array a0 a1 b0 b1 gt gt gt y np array x0 x1 y0 y1 gt gt gt iterable np outer x i y i for i in xrange x sha
  • pandas to_sql sqlalchemy 与 secure_transport 的连接

    我正在尝试将数据发送到具有 require secure transport ON 的服务器上的 mysql 数据库 当我尝试使用以下代码连接到它时 import pandas as pd import pymysql from sqlal
  • 使 np.loadtxt 使用多个可能的分隔符

    我有一个程序可以读取数据文件 用户可以选择他们想要使用的列 我希望它对于输入文件更加通用 有时 列可能如下所示 10 34 24 58 8 284 6 121 有时它们可 能看起来像这样 10 34 24 58 8 284 6 121 我希
  • PyCharm - 如何挂起所有线程

    我们使用 PyCharm 5 0 1 进行多线程调试 当它在断点处停止时 只有特定线程停止 而所有其他线程继续 这使得 冻结时刻 和检查参数值以及其他线程的当前状态变得困难 当其中一个线程在断点处停止时 是否可以挂起所有线程 这在最新的 P
  • 如何加速 pandas 字符串函数?

    我正在使用 pandas 矢量化 str split 方法来提取从 上的拆分 返回的第一个元素 我还尝试使用 df apply 与 lambda 和 str split 来产生等效的结果 使用 timeit 时 我发现 df apply 的
  • Python 中的十进制到二进制半精度 IEEE 754

    我只能使用以下命令将十进制转换为二进制单精度 IEEE754struct pack模块 或者使用相反的方法 float16 或 float32 numpy frombuffer 是否可以使用 Numpy 将十进制转换为二进制半精度浮点数 我
  • 如何使用 pygame.mixer 重复音乐?

    我创建了以下使用 pygame mixer 播放 mp3 音乐的代码 然而 音乐不会重复 有什么想法可以让音乐重复播放吗 这是代码 playlist list playlist append put music here mp3 playl
  • Scrapy 抓取并跟踪 href 中的链接

    我对 scrapy 很陌生 我需要从 url 的主页跟踪 href 到多个深度 再次在 href 链接内我有多个 href 我需要遵循这些href 直到到达我想要抓取的页面 我的页面的示例 html 是 初始页 div class page
  • Flask 扩展未在 app.extensions 中注册

    我想访问在我的 Flask 应用程序上注册的一些扩展 我尝试使用app extensions 但我初始化的一些扩展不在字典中 from flask import current app current app extensions get
  • Matplotlib 中的 TwoSlopeNorm 未按预期工作

    我正在尝试创建一个具有发散颜色图的绘图 该颜色图在零附近不对称 In this https stackoverflow com a 20146989 6288682例如 DivergingNorm函数被使用并产生我想要的 然而 我使用的是更
  • 通过 ManyToManyField = Value 对 django 查询集进行排序

    如果有一些模型 例如 class Tag models Model name models CharField class Thing models Model title models CharField tags models Many

随机推荐