• 这个字典库引起了 Python 之父的注意!你用过吗?


    【导语】:本文介绍了Bi-Dictionary 库,即“Bi-directional Dictionary”双向字典,顾名思义,该库基于Python中的字典增加了由“值”访问键的功能,开发者可以通过值来反向查找键,使得处理字典更加方便。同时,该库也引起了 Python 之父 Guido 的注意,因此,很有必须学习Bi-Dictionary 库。

    简介

    字典是Python中最常见的数据结构之一,在日常开发中使用的频率很高。字典由一些键值对构成,我们只能通过键访问值,但是无法通过值访问键。目前有一个第三方库很好的解决了这个问题 - Bi-Dictionary,通过使用它,我们可以由值访问键。该库甚至引起了 Python 之父 Guido 的注意,因此这一特性未来可能会被加入到Python语法中。

    安装

    我们可以使用pip安装bidict库:

    pip install bidict

    随后,需要导入该库才能使用:

    from bidict import bidict

    简单使用

    1. 初步使用

    我们首先通过创建一个字典,该字典的键为国家的简称,值为国家的全名,再用bidict初始化这个字典:

    country_abbr_bidict = bidict({'USA': 'The United States of America'})

    这样,我们只需要使用inverse()方法,就可以通过国家全称获取国家简称了:

    1. from bidict import bidict
    2. country_abbr_bidict = bidict({'USA''The United States of America'})
    3. shortName = country_abbr_bidict.inverse['The United States of America']
    4. print(shortName)

    结果为:USA

    我们可以对比下原字典和反转后的区别:

    1. from bidict import bidict
    2. country_abbr_bidict = bidict({'USA''The United States of America'})
    3. print(country_abbr_bidict)
    4. print(country_abbr_bidict.inverse)

    结果显示,inverse()方法反转了原字典的键值位置:

    1. bidict({'USA''The United States of America'})
    2. bidict({'The United States of America''USA'})
    1. 为何不使用Python的字典呢?

    我们也可以在字典中把键值互换,再存储一份数据,这样也能实现与bidict相同的效果。我们来尝试一下:

    1. country_abbr_dict = {
    2.     'USA''The United States of America',
    3.     'The United States of America''USA'
    4. }

    如果我们想把USA更新成US,可以使用update()方法,像下面这样:

    1. country_abbr_dict.update({
    2.     'US''The United States of America',
    3.     'The United States of America''US'
    4. })

    这似乎看起来很完美,但是字典仍然保留了原来的数据:

    1. from bidict import bidict
    2. country_abbr_dict = {
    3.     'USA''The United States of America',
    4.     'The United States of America''USA'
    5. }
    6. country_abbr_dict.update({
    7.     'US''The United States of America',
    8.     'The United States of America''US'
    9. })
    10. print(country_abbr_dict)

    在结果中我们可以看到USA也在字典中:

    {'USA': 'The United States of America', 'The United States of America': 'US', 'US': 'The United States of America'}

    为了避免这个问题,只能定义一个函数:

    1. def update(d, key, val):
    2.     oldval = d.pop(key, object())
    3.     d.pop(oldval, None)
    4.     oldkey = d.pop(val, object())
    5.     d.pop(oldkey, None)
    6.     d.update({key: val, val: key})
    7. country_abbr_dict = {
    8.     'USA''The United States of America',
    9.     'The United States of America''USA'
    10. }
    11. update(country_abbr_dict, 'US''The United States of America')
    12. print(country_abbr_dict)

    这样就可以成功更新字典了:

    {'US': 'The United States of America', 'The United States of America': 'US'}

    如果使用Bidict,就非常简单了:

    1. country_abbr_bidict.inverse['The United States of America'] = 'US'
    2. print(country_abbr_bidict)

    bidict({'US': 'The United States of America'})

    Bidict用起来,明显更方便!

    1. Bidict的其他用途

    • 在查找值之前,传入默认值

    Bidict继承了Python字典中的大部分特性。例如,当我们想要通过键访问bidict中的某个值时,可以传入一个默认值。这样,如果bidict中没有该值,就会将默认值作为结果返回。

    1. from bidict import bidict
    2. country_abbr_bidict = bidict({
    3.     'US''The United States of America',
    4. })
    5. print(country_abbr_bidict.get('AU''Australia'))

    结果就是我们传入的默认值:Australia

    • 加入新的键值对

    Bidict加入新键值对的方式与Python的原生字典一样,我们来试试:

    1. from bidict import bidict
    2. country_abbr_bidict = bidict({
    3.     'US''The United States of America',
    4. })
    5. country_abbr_bidict['AU'] = 'Australia'
    6. country_abbr_bidict['CA'] = 'Canada'
    7. print(country_abbr_bidict)

    结果为:

    bidict({'US': 'The United States of America', 'AU': 'Australia', 'CA': 'Canada'})

    • 检验Bidict中是否有某个特定值

    (1)我们可以使用in关键字来检查Bidict中是否有CA:

    'CA' in country_abbr_bidict

    我们可以得到一个布尔值,表示该键是否存在于Bidict中:True

    (2)同样我们也可以检查Bidict中是否有某个值,

    'Australia' in country_abbr_bidict.inverse

    结果显示Bidict中有该值:True

    • Pop and Delete方法

    除了上述特性外,我们还可以使用Pop and Delete方法。

    (1)pop()方法可以从Bidict中弹出键值对

    country_abbr_bidict.pop('AU')

    会返回该键对应的值:Australia

    我们再看看Bidict:country_abbr_bidict

    发现里面没有AU这个键值对了:bidict({'US': 'The United States of America', 'CA': 'Canada'})

    (2)delete()方法可以通过键或者值的方式删除键值对

    1. del country_abbr_bidict.inverse['Canada']
    2. print(country_abbr_bidict)

    结果显示删除成功:bidict({'US': 'The United States of America'})

    1. 约束

    Python的设计理念是当程序出现错误时,一定要显示出来,Bidict的设计也遵循了这一点。Bidict的一个约束是键、值都要唯一,这是因为值也有可能会被当作键使用。因此,当我们想在Bidict中加入一个新的键值对(该键值对的值已经被其他键使用),就会报错。例如,我们想把US - The United States of America加入Bidict中,但是原字典中已有USA - The United States of America了:

    1. from bidict import bidict
    2. country_abbr_bidict = bidict({
    3.     'USA''The United States of America',
    4. })
    5. country_abbr_bidict['US'] = 'The United States of America'

    会产生如下错误:

    1. Traceback (most recent call last):
    2.   File "F:/Documents/其他资料/pythonprojects/01practice/app.py", line 5, in <module>
    3.     country_abbr_bidict['US'] = 'The United States of America'
    4.   File "F:\python\lib\site-packages\bidict\_bidict.py", line 67, in __setitem__
    5.     self.put(key, val, on_dup=self.on_dup)
    6.   File "F:\python\lib\site-packages\bidict\_bidict.py", line 93, in put
    7.     self._update([(key, val)], on_dup=on_dup)
    8.   File "F:\python\lib\site-packages\bidict\_base.py", line 455, in _update
    9.     dedup_result = self._dedup(key, val, on_dup)
    10.   File "F:\python\lib\site-packages\bidict\_base.py", line 350, in _dedup
    11.     raise ValueDuplicationError(val)
    12. bidict.ValueDuplicationError: The United States of America

    我们可以使用forceput()方法来避免这一错误:country_abbr_bidict.forceput('USA', 'The United States of America')

    但是,如果出现了两个键的值相同这种情况,该方法会把原来的键覆盖:bidict({'US': 'The United States of America'})

    1. 其他特性

    • 更新多个键值对

    putall()方法可以同时加入多个键值对到Bidict中,但传入的参数必须是可迭代的。

    1. country_abbr_bidict.putall([
    2.     ('AU''Australia'),
    3.     ('CA''Canada')
    4. ])
    5. print(country_abbr_bidict)

    结果显示加入成功:bidict({'USA': 'The United States of America', 'AU': 'Australia', 'CA': 'Canada'})

    当某个键值对无法传入时,那么其他键值对也无法传入:

    1. country_abbr_bidict = bidict({'US''United States of America'})
    2. country_abbr_bidict.putall([
    3.     ('AU''Australia'),
    4.     ('CA''Canada'),
    5.     ('US''The United States of America')
    6. ])

    这里出现了报错:

    1. Traceback (most recent call last):
    2.   File "F:/Documents/其他资料/pythonprojects/01practice/app.py", line 3, in <module>
    3.     country_abbr_bidict.putall([
    4.   File "F:\python\lib\site-packages\bidict\_bidict.py", line 179, in putall
    5.     self._update(items, on_dup=on_dup)
    6.   File "F:\python\lib\site-packages\bidict\_base.py", line 443, in _update
    7.     target._update(arg, kw, rbof=False, on_dup=on_dup)
    8.   File "F:\python\lib\site-packages\bidict\_base.py", line 455, in _update
    9.     dedup_result = self._dedup(key, val, on_dup)
    10.   File "F:\python\lib\site-packages\bidict\_base.py", line 343, in _dedup
    11.     raise KeyDuplicationError(key)
    12. bidict.KeyDuplicationError: US

    而其他键值对也没有传入到Bidict中:bidict({'US': 'United States of America'})

    • forceupdate()方法的优先级

    如果我们想使用该方法传入多个键值对,对Bidict进行更新,那么就要注意传入数据的先后顺序了。

    如果把USA放到最后,那么最终Bidict就会使用该键:

    1. country_abbr_bidict = bidict({'US''United States of America'})
    2. country_abbr_bidict.forceupdate([
    3.     ('US''The United States of America'),
    4.     ('USA''The United States of America')
    5. ])

    结果为:bidict({'USA': 'The United States of America'})

    如果把US放到最后,那么字典就会将US作为键。

    1. country_abbr_bidict.forceupdate([
    2.     ('USA''The United States of America'),
    3.     ('US''The United States of America')
    4. ])
    5. print(country_abbr_bidict)

    结果为:bidict({'US': 'The United States of America'})

    • 与其他数据结构交互

    Bidict可以转换为其他数据结构,反之亦然。例如,我们可以把Bidict转换为字典:dict(country_abbr_bidict)

    结果为:{'US': 'United States of America'}

    我们再把字典转换为Bidict: bidict(dict(country_abbr_bidict))

    结果为:bidict({'US': 'United States of America'})

    结论

    在本文中,我介绍了Bi-Dictionary库-双向字典,也称为Bidict。它不仅改进了Python字典的缺点,而且遵循了Python的设计原则。非常值得学习!

    参考原文:
    https://towardsdatascience.com/python-bi-dictionary-key-can-be-value-and-value-can-be-key-50715a2046af

    - EOF -

    outside_default.png

    加主页君微信,不仅Python技能+1

    outside_default.png5992ffda14d9dbde97e5695b1d1c6163.png

    主页君日常还会在个人微信分享Python相关工具资源精选技术文章,不定期分享一些有意思的活动岗位内推以及如何用技术做业余项目

    2d893be13fa5b2c2933820ed410fc2ab.jpeg

    加个微信,打开一扇窗

    推荐阅读  点击标题可跳转

    1、orjson:功能丰富的高性能 Python JSON 库

    2、很期待!尝鲜 Python 3.11 的 5 个新特性

    3、抓取速度提升 3 倍!Python 的这个内置库你用上了吗?

    觉得本文对你有帮助?请分享给更多人

    推荐关注「Python开发者」,提升Python技能

    点赞和在看就是最大的支持❤️

  • 相关阅读:
    qcustemplot使用opengl加速
    RE2:Simple and Effective Text Matching with Richer Alignment Features
    真实环绕的魅力,飞利浦杜比全景声影院B8967开箱
    03 转换css元素的类别
    (windows ssh) windows开启ssh服务,并通过ssh登录该win主机
    偶数科技为辽宁农信数字化进程添加新动能
    Spring()
    图斑自上而下,自左而右顺序编码,按照权属单位代码分组,每组从1开始编码
    数学建模| 快速入门(以华为杯2019F题为例)
    JavaScript 中常用和必备的一些工具类函数
  • 原文地址:https://blog.csdn.net/iodjSVf8U1J7KYc/article/details/125611163