如何检查一个对象是否是namedtuple的实例?

发布于 2024-08-19 20:28:16 字数 170 浏览 6 评论 0 原文

如何检查对象是否是 命名元组

How do I check if an object is an instance of a Named tuple?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(7

不羁少年 2024-08-26 20:28:16

调用函数 collections.namedtuple 会为您提供一个新类型,它是 tuple 的子类(并且没有其他类),并且具有名为 的成员_fields 这是一个元组,其项目都是字符串。因此,您可以检查每一项:

def isnamedtupleinstance(x):
    t = type(x)
    b = t.__bases__
    if len(b) != 1 or b[0] != tuple: return False
    f = getattr(t, '_fields', None)
    if not isinstance(f, tuple): return False
    return all(type(n)==str for n in f)

有可能从中得到误报,但前提是有人不遗余力地创建一种看起来很多像命名元组但不是一个;-)。

Calling the function collections.namedtuple gives you a new type that's a subclass of tuple (and no other classes) with a member named _fields that's a tuple whose items are all strings. So you could check for each and every one of these things:

def isnamedtupleinstance(x):
    t = type(x)
    b = t.__bases__
    if len(b) != 1 or b[0] != tuple: return False
    f = getattr(t, '_fields', None)
    if not isinstance(f, tuple): return False
    return all(type(n)==str for n in f)

it IS possible to get a false positive from this, but only if somebody's going out of their way to make a type that looks a lot like a named tuple but isn't one;-).

亣腦蒛氧 2024-08-26 20:28:16

如果你想确定一个对象是否是特定namedtuple的实例,你可以这样做:

from collections import namedtuple

SomeThing = namedtuple('SomeThing', 'prop another_prop')
SomeOtherThing = namedtuple('SomeOtherThing', 'prop still_another_prop')

a = SomeThing(1, 2)

isinstance(a, SomeThing) # True
isinstance(a, SomeOtherThing) # False

If you want to determine whether an object is an instance of a specific namedtuple, you can do this:

from collections import namedtuple

SomeThing = namedtuple('SomeThing', 'prop another_prop')
SomeOtherThing = namedtuple('SomeOtherThing', 'prop still_another_prop')

a = SomeThing(1, 2)

isinstance(a, SomeThing) # True
isinstance(a, SomeOtherThing) # False
挽你眉间 2024-08-26 20:28:16

3.7+

def isinstance_namedtuple(obj) -> bool:
    return (
            isinstance(obj, tuple) and
            hasattr(obj, '_asdict') and
            hasattr(obj, '_fields')
    )

3.7+

def isinstance_namedtuple(obj) -> bool:
    return (
            isinstance(obj, tuple) and
            hasattr(obj, '_asdict') and
            hasattr(obj, '_fields')
    )

三月梨花 2024-08-26 20:28:16

如果您需要在调用namedtuple特定函数之前进行检查,那么只需调用它们并捕获异常即可。这是在 python 中执行此操作的首选方法。

If you need to check before calling namedtuple specific functions on it, then just call them and catch the exception instead. That's the preferred way to do it in python.

人疚 2024-08-26 20:28:16

改进 Lutz 发布的内容:

def isinstance_namedtuple(x):                                                               
  return (isinstance(x, tuple) and                                                  
          isinstance(getattr(x, '__dict__', None), collections.Mapping) and         
          getattr(x, '_fields', None) is not None)                                  

Improving on what Lutz posted:

def isinstance_namedtuple(x):                                                               
  return (isinstance(x, tuple) and                                                  
          isinstance(getattr(x, '__dict__', None), collections.Mapping) and         
          getattr(x, '_fields', None) is not None)                                  
囚你心 2024-08-26 20:28:16

在我看来,我使用

isinstance(x, tuple) and isinstance(x.__dict__, collections.abc.Mapping)

的似乎最能反映命名元组性质的字典方面。
它对于一些可以想象的未来变化似乎也很强大,并且也可能与许多第三方命名元组类一起使用,如果这样的事情碰巧存在的话。

I use

isinstance(x, tuple) and isinstance(x.__dict__, collections.abc.Mapping)

which to me appears to best reflect the dictionary aspect of the nature of named tuples.
It appears robust against some conceivable future changes too and might also work with many third-party namedtuple-ish classes, if such things happen to exist.

孤者何惧 2024-08-26 20:28:16

IMO 这可能是 Python 3.6 及更高版本的最佳解决方案。

您可以在实例化命名元组时设置自定义 __module__,稍后检查它,

from collections import namedtuple

# module parameter added in python 3.6
namespace = namedtuple("namespace", "foo bar", module=__name__ + ".namespace")

然后检查 __module__

if getattr(x, "__module__", None) = =“xxxx.命名空间”:

IMO this might be the best solution for Python 3.6 and later.

You can set a custom __module__ when you instantiate your namedtuple, and check for it later

from collections import namedtuple

# module parameter added in python 3.6
namespace = namedtuple("namespace", "foo bar", module=__name__ + ".namespace")

then check for __module__

if getattr(x, "__module__", None) == "xxxx.namespace":

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文