V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
推荐学习书目
Learn Python the Hard Way
Python Sites
PyPI - Python Package Index
http://diveintopython.org/toc/index.html
Pocoo
值得关注的项目
PyPy
Celery
Jinja2
Read the Docs
gevent
pyenv
virtualenv
Stackless Python
Beautiful Soup
结巴中文分词
Green Unicorn
Sentry
Shovel
Pyflakes
pytest
Python 编程
pep8 Checker
Styles
PEP 8
Google Python Style Guide
Code Style from The Hitchhiker's Guide
billgreen1
V2EX  ›  Python

如何通过点(dot)来获得字典的属性?

  •  
  •   billgreen1 · 2016-02-04 11:19:56 +08:00 · 3425 次点击
    这是一个创建于 3216 天前的主题,其中的信息可能已经有所发展或是发生改变。

    现在用的是 dict of dict 的方式来表达数据。嵌套层次大概 3-4 层这样。

    {
        'CatagoryA': {
                               'sub_catagory1':{
                                                           'sub_sub_catagory1':{},
                                                           ...
                                                         },
                               ...
                            },
        'CatagoryB':{
                             ...
                           },
         ...
    
    }
    

    不方便的地方在于记不住键。

    我能想到的处理方法是把每个字典换做用一个类,然后用类嵌套类的方式来实现。
    这样可以比较方便的用代码提示功能。

    希望能有更好的办法。谢谢。

    6 条回复    2016-02-04 19:39:36 +08:00
    Karblue
        1
    Karblue  
       2016-02-04 11:42:30 +08:00
    大概只能这么做。
    ```python
    class MyDict(dict):
    __getattribute__ = __getitem__
    ```
    onlyice
        2
    onlyice  
       2016-02-04 11:43:40 +08:00 via Android
    @Karblue 你没看清楚楼主的要求,他希望的是 IDE 能够给自动提示
    hahastudio
        3
    hahastudio  
       2016-02-04 11:49:20 +08:00
    重写 __getattr__ __setattr__
    http://stackoverflow.com/questions/2352181/how-to-use-a-dot-to-access-members-of-dictionary
    http://code.activestate.com/recipes/576586-dot-style-nested-lookups-over-dictionary-based-dat/

    用函数去接受这种特殊的查询字符串
    http://stackoverflow.com/questions/12414821/checking-a-dictionary-using-a-dot-notation-string

    但是你要注意,你的 key 永远都不能有 dot 了,所以其实是不等价的
    至于你说的代码提示,不知道这种方式会不会有提示,估计没有
    --话说为什么要用 js 的方式去写 Python ,这又不是 json--
    Karblue
        4
    Karblue  
       2016-02-04 11:54:39 +08:00
    @onlyice 好吧~没看清。 LZ 可以试试 Pycharm 大部分提示可以搞定。包括手动赋值的 dict
    lianghui
        5
    lianghui  
       2016-02-04 12:04:02 +08:00
    ```python
    class SelectConfig(object):

    def __init__(self, config=None):
    self._config = config or {}

    def set(self, key, value):
    keys = self._keys(key)
    config = self._config
    i = 0
    for k in keys:
    if isinstance(config, dict) and k in config:
    if i == len(keys) - 1:
    config[k] = value
    return
    config = config[k]
    i += 1

    keys = keys[i:]
    last_key = keys.pop()
    for k in keys:
    config[k] = {}
    config = config[k]
    config[last_key] = value

    def get(self, key=None, default=None):
    keys = self._keys(key)
    config = self._config
    for k in keys:
    if k in config:
    config = config[k]
    else:
    config = default
    break

    return config

    def delete(self, key):
    keys = self._keys(key)
    if len(keys) == 2:
    v = self.get(keys[0])
    if isinstance(v, dict):
    del v[keys[1]]
    else:
    del self._config[keys[0]]

    def update(self, config):
    for k, v in config.items():
    self.set(k, v)

    def __contains__(self, key):
    keys = self._keys(key)
    contains = True
    config = self._config
    for k in keys:
    if k in config:
    config = config[k]
    else:
    contains = False
    break

    return contains

    def _keys(self, key):
    return key.split('.')

    def __json__(self):
    return self._config
    ```
    Anthony117
        6
    Anthony117  
       2016-02-04 19:39:35 +08:00
    ```python
    class Dict(dict):
    '''
    Simple dict but support access as x.y style.
    '''
    def __init__(self, d):
    super(Dict, self).__init__()
    for k, v in d.items():
    self[k] = Dict(v) if isinstance(v, dict) else v

    def __getattr__(self, key):
    try:
    return self[key]
    except KeyError:
    raise AttributeError(r"'Dict' object has no attribute '%s'" % key)

    def __setattr__(self, key, value):
    self[key] = value
    ```

    使用:
    ```python
    >>> dic = Dict({'a':1,'b':2})
    >>> dic.b
    2
    ```


    修改自廖雪峰的 python 教程:
    http://www.liaoxuefeng.com/wiki/0014316089557264a6b348958f449949df42a6d3a2e542c000/001432339034336cbf72acd43354d72831461e3871d9f2e000
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   2732 人在线   最高记录 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 26ms · UTC 11:21 · PVG 19:21 · LAX 03:21 · JFK 06:21
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.