iis服务器助手广告广告
返回顶部
首页 > 资讯 > 后端开发 > Python >解读Python中字典的key都可以是什么
  • 525
分享到

解读Python中字典的key都可以是什么

2024-04-02 19:04:59 525人浏览 独家记忆

Python 官方文档:入门教程 => 点击学习

摘要

目录python字典的key都可以是什么答解释注意Python字典的key都可以是什么 答 一个对象能不能作为字典的key,就取决于其有没有__hash__方法。所以所有python

Python字典的key都可以是什么

一个对象能不能作为字典的key,就取决于其有没有__hash__方法。所以所有python自带类型中,除了list、dict、set和内部至少带有上述三种类型之一的tuple之外,其余的对象都能当key。

比如数值/字符串/完全不可变的元祖/函数(内建或自定义)/类(内建或自定义)/方法/包等等你能拿出手的,不过有的实际意义不高。还有数值型要注意,因为两个不同的相等数字可以有相同的哈希值,比如1和1.0。

解释

代码版本:3.6.3;文档版本:3.6.6

Unlike sequences, which are indexed by a range of numbers, dictionaries are indexed by keys, which can be any immutable type; strings and numbers can always be keys. Tuples can be used as keys if they contain only strings, numbers, or tuples; if a tuple contains any mutable object either directly or indirectly, it cannot be used as a key. You can’t use lists as keys, since lists can be modified in place using index assignments, slice assignments, or methods like append()and extend().

 字典的键可以是任意不可变类型,需要注意的是tuple元组作为键时,其中不能以任何方式包含可变对象。

 那。。到底什么样的是不可变类型呢?不可能给对象专门标注一个属性是可变类型还是不可变类型啊,这没有任何其他意义,一定是通过其他途径实现的。把list当做键试一下

a = [1, 2, 3]
d = {a: a}
 
 
# 第二行报错:
# TypeError: unhashable type: 'list'

报错说list类型是不可哈希的,噢,原来是靠能不能hash来判断的,另外文档下面接着说同一字典中每个键都是唯一的,正好每个对象的哈希值也是唯一的,对应的很好。

It is best to think of a dictionary as an unordered set of key: value pairs, with the requirement that the keys are unique (within one dictionary).

查看源代码可以看到object对象是定义了__hash__方法的,

而list、set和dict都把__hash__赋值为None了

# 部分源码
 
class object:
    """ The most base type """
 
    def __hash__(self, *args, **kwargs):  # real signature unknown
        """ Return hash(self). """
        pass
 
 
class list(object):
    __hash__ = None
 
 
class set(object):
    __hash__ = None
 
 
class dict(object):
    __hash__ = None

那这样的话。。。我给他加一个hash不就能当字典的key了,key不就是可变的了。

注意

此处只是我跟着想法随便试,真的应用场景不要用可变类型作为字典的key。

class MyList(list):
    """比普通的list多一个__hash__方法"""
 
    def __hash__(self):
        # 不能返回hash(self)
        # hash(self)会调用self的本方法,再调用回去,那就没完了(RecursionError)
        # 用的时候要注意实例中至少有一个元素,不然0怎么取(IndexError)
        return hash(self[0])
 
 
l1 = MyList([1, 2])  # print(l1) -> [1, 2]
d = {l1: 'Can?'}
print(d)  # -->  {[1, 2]: 'Can?'}
l1.append(3)
print(d)  # {[1, 2, 3]: 'Can?'}
print(d[l1])  # -->  Can?

到这里就可以肯定的说,一个对象能不能作为字典的key,就取决于其有没有__hash__方法。所以所有python自带类型中,目前我已知的除了list、dict、set和内部带有以上三种类型的tuple之外,其余的对象都能当key。而我们自己定义的类,一般情况下都直接间接的和object有关,都带有__hash__方法。

另外我想到,既然字典的键是唯一的,而哈希值也是唯一的,这么巧,键的唯一性不会就是用哈希值来确定的吧?我上一个例子中__hash__方法返回的是0号元素的哈希值,那我直接用相同哈希值的对象是不是就能改变那本来不属于它的字典值呢?

class MyList(list):
    def __hash__(self):
        return hash(self[0])
 
 
l1 = MyList([1, 2])  # print(l1) -> [1, 2]
d = {}
d[l1] = l1
print(d)  # {[1, 2]: [1, 2]}
d[1] = 1
print(d)  # {[1, 2]: [1, 2], 1: 1}

竟然没有改成功而是新添加了一个键值对,可self[0]就是1啊,哈希值一样啊,怎么会不一样呢?难道要键的值一样才能判断是同一个键吗?重写__eq__方法试一下。

class MyList(list):
    def __hash__(self):
        return hash(self[0])
 
    def __eq__(self, other):
        return self[0] == other
 
 
l1 = MyList([1, 2])  # print(l1) -> [1, 2]
d = {}
d[l1] = l1
print(d)  # {[1, 2]: [1, 2]}
d[1] = 1
print(d)  # {[1, 2]: 1}

这回成功了,那就是__hash__返回值相等,且eq判断也相等,才会被认为是同一个键。那这两个先判断哪个呢?加个代码试一下

class MyList(list):
    def __hash__(self):
        print('hash is run')
        return hash(self[0])
 
    def __eq__(self, other):
        print('eq is run')
        return self[0] == other
 
 
l1 = MyList([1, 2])  # print(l1) -> [1, 2]
d = {}
d[1] = 1
d[l1] = 'l1'
print(d)
 
 
# 结果:
# hash is run
# eq is run
# {1: 'l1'}

__hash__先执行,另外字典在内存中存储数据的位置和键的hash也是有关的,逻辑上也像印证。

先计算hash,找到相对应的那片内存空间,里面没有值的话就直接写入,对于字典来说就是新增键值对;如果里面已经有值了,那就判断新来的键和原来的那里的键是不是相等,相等就认为是一个键,对于字典来说就是更新值,不相等就再开空间,相当于字典新增键值对。

在你验证自己想法的时候可能遇到__hash__和__eq__的一些想不到的麻烦,可以看这里:__hash__和__eq__的继承使用问题

以上为个人经验,希望能给大家一个参考,也希望大家多多支持编程网。

--结束END--

本文标题: 解读Python中字典的key都可以是什么

本文链接: https://www.lsjlt.com/news/120638.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
  • 解读Python中字典的key都可以是什么
    目录Python字典的key都可以是什么答解释注意Python字典的key都可以是什么 答 一个对象能不能作为字典的key,就取决于其有没有__hash__方法。所以所有python...
    99+
    2024-04-02
  • python字典查找key的方法是什么
    在Python中,可以使用以下方法来查找字典中的键:1. 使用索引操作符([]):可以通过使用键作为索引来访问字典中的值。如果键不存...
    99+
    2023-09-20
    python
  • python中字典的键可以为哪些类型
    python中字典是一种可变容器模型,可以存储任意类型的对象,其中字典的值可以取任何数据类型,但字典的键必须是不可变类型,如字符串、数字和元组等。...
    99+
    2024-04-02
  • python字典保存和读取的方法是什么
    在Python中,可以使用pickle模块来保存和读取字典。保存字典到文件:```import picklemy_dict = {'...
    99+
    2023-08-08
    python
  • Python中字典的特性是什么
    Python中字典的特性是什么?相信很多没有经验的人对此束手无策,为此本文总结了问题出现的原因和解决方法,通过这篇文章希望你能解决这个问题。python主要应用领域有哪些1、云计算,典型应用OpenStack。2、WEB前端开发,众多大型网...
    99+
    2023-06-14
  • python中字典的概念是什么
    这篇文章给大家分享的是有关python中字典的概念是什么的内容。小编觉得挺实用的,因此分享给大家做个参考,一起跟随小编过来看看吧。字典的概念字典和列表类似,也是可变序列,不过和列表不同,它是无序的可变序列,...
    99+
    2024-04-02
  • python字典指的是什么
    这篇文章主要介绍了python字典指的是什么,具有一定借鉴价值,感兴趣的朋友可以参考下,希望大家阅读完这篇文章之后大有收获,下面让小编带着大家一起了解一下。python是什么意思Python是一种跨平台的、具有解释性、编译性、互动性和面向对...
    99+
    2023-06-14
  • 浅谈Python的字典键名可以是哪些类型
    目录1 键的类型,列表/字典不可以,其它都可以2 多个对象可当作键名,顺序不同时是不同的键3 结论【有误】:今天看别人代码时发现一个事,就是把对象当作字典的键名,并且把两个对象(类的...
    99+
    2024-04-02
  • Python字典和常规字典的区别是什么
    这篇文章主要讲解了“Python字典和常规字典的区别是什么”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“Python字典和常规字典的区别是什么”吧!用一个实例来说明排序后的字典和常规字典之间...
    99+
    2023-06-17
  • python中字典和集合是什么
    这篇文章主要介绍了python中字典和集合是什么,具有一定借鉴价值,感兴趣的朋友可以参考下,希望大家阅读完这篇文章之后大有收获,下面让小编带着大家一起了解一下。字典/集合理解就像我们使用列表推导一样,我们也可以使用字典/集合推导。它们易于使...
    99+
    2023-06-27
  • python怎么读取列表中字典的value值
    这篇文章将为大家详细讲解有关python怎么读取列表中字典的value值,小编觉得挺实用的,因此分享给大家做个参考,希望大家阅读完这篇文章后可以有所收获。读取列表中字典的value值list = [{"name...
    99+
    2023-06-29
  • python中key的用法是什么
    在Python中,key是用于指定排序的规则的参数。在一些排序函数或方法中,可以通过指定key参数来自定义排序的规则。例如,在使用s...
    99+
    2024-03-01
    python
  • 解读Python中的frame是什么
    目录Python中的frame是什么栈帧(frame)Python的frame对象特殊的只读属性特殊可写属性Python中的frame是什么 栈帧(frame) 栈帧表示程序运行时函...
    99+
    2022-11-13
    Python frame是什么 Python的frame Python frame
  • python中defaultdict字典功能特性是什么
    这篇文章主要介绍python中defaultdict字典功能特性是什么,文中介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们一定要看完!defaultdict是普通字典dict的一个子类。通过collections库的defaultdi...
    99+
    2023-06-29
  • python字典创建的方法是什么
    Python字典有多种创建的方法,以下是几种常见的方法: 使用花括号{}创建一个空字典: my_dict = {} 使用花括...
    99+
    2023-10-23
    python
  • python字典合并的规范是什么
    本篇内容介绍了“python字典合并的规范是什么”的有关知识,在实际案例的操作过程中,不少人都会遇到这样的困境,接下来就让小编带领大家学习一下如何处理这些情况吧!希望大家仔细阅读,能够学有所成!1、字典合并返回新字典,该字典由左操作数和右操...
    99+
    2023-06-30
  • python字典合并的特点是什么
    这篇文章主要介绍了python字典合并的特点是什么的相关知识,内容详细易懂,操作简单快捷,具有一定借鉴价值,相信大家阅读完这篇python字典合并的特点是什么文章都会有所收获,下面我们一起来看看吧。概念Python中的字典可以像集合一样使用...
    99+
    2023-06-30
  • python字典赋值的方法是什么
    Python中的字典是一种无序的键值对集合,每个键值对之间用逗号分隔,整个字典用花括号{}括起来表示。字典中的键必须是唯一的,而值可...
    99+
    2023-05-13
    python字典赋值 python
  • Python字典的运算方法是什么
    本篇内容介绍了“Python字典的运算方法是什么”的有关知识,在实际案例的操作过程中,不少人都会遇到这样的困境,接下来就让小编带领大家学习一下如何处理这些情况吧!希望大家仔细阅读,能够学有所成!问题描述怎样在数据字典中执行一些计算操作(比如...
    99+
    2023-06-22
  • Python中字典存储元组的方法是什么
    在Python中,可以使用字典来存储元组。字典中的元素是以键值对的形式存储的,其中键可以是任意不可变的数据类型,比如字符串、整数、元...
    99+
    2024-04-23
    Python
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作