Python Flask高级编程

推荐的学习视频教程是:Python Flask高级编程

通过学习这些优秀开源项目的源码,不但可以开阔自己视野,还能达到提高Python编码水平的目的。

本文将依次介绍以下几个对Python字典的扩展:

  • Storage 封装字典操作提供便利性
  • ImmutiDict 一旦赋值、不可修改的字典
  • CaseSentiveDict Key大小写不敏感的通用字典

1. Storage

1.1 Storage的作用

Storage是web.py的作者为了更方便的使用字典,进行的简单封装。封装完成以后,既可以通过点运算符(d.a)访问字典的项,也可以通过Python内置的方式(d['a'])访问字典项。显然,使用Storage进行封装以后,访问字典可以少敲很多字符,这就是Storage提供的便利性。

1.2 Storage的源码

Storage的具体实现如下,为了便于大家更直观的感受Storage的用法,我对Storage的文档进行了简单修改:

class Storage(dict): """  A Storage object is like a dictionary except `obj.foo` can be used  in addition to `obj['foo']`.  o = Storage(a=1, b=2, c=3)  >>> print o  <Storage {'a': 1, 'c': 3, 'b': 2}>  >>> o.a = 2  >>> print o  <Storage {'a': 2, 'c': 3, 'b': 2}>  >>> o.d = 4  >>> print o  <Storage {'a': 2, 'c': 3, 'b': 2, 'd': 4}>  >>> del o.b  >>> print o  <Storage {'a': 2, 'c': 3, 'd': 4}>  >>> o.b  Traceback (most recent call last):  ...  AttributeError: 'b'  """ def __getattr__(self, key): try: return self[key] except KeyError as k: raise AttributeError(k) def __setattr__(self, key, value): self[key] = value def __delattr__(self, key): try: del self[key] except KeyError as k: raise AttributeError(k) def __repr__(self): return '<Storage ' + dict.__repr__(self) + '>' 

1.3 Storage的实现解析

Storage的实现非常简单,除去为了友好的显示提供的__repr__函数以外,仅包含三个与属性相关的特殊函数,分别是__getattr__, __setattr__, __delattr__。显然,这三个特殊函数就是实现字典的增删改查操作的特殊函数。Storage拦截了这三个操作,并重新应用到内置字典的操作中,以此来提供一个操作更加方便的字典。

可以看到,Storage的实现非常简单,但是,Storage确是一个 很好的教学项目:1)可以通过Storage了解如何扩展内置字典;2)通过Storage了解Python的运算符重载的应用。

2. ImmutableDict

ImmutableDict是werkzeug中的实现的不可变字典。werkzeug是WSGI工具集,也是Flask的依赖,由Flask的作者实现。Flask是目前Python生态中最流行的Web框架(之一?)。

2.1 ImmutableDict的使用

ImmutableDict的使用很简单也很直接,就是创建一个不可修改的字典。字典一旦创建成功,就只能访问,不能进行任何修改操作,也不能删除字典中的元素。如下所示:

    def main():
        d = ImmutableDict(a=1, b=2, c=3) print(d) # ImmutableDict({'a': 1, 'c': 3, 'b': 2}) # d['d'] = 4 # TypeError: 'ImmutableDict' objects are immutable if __name__ == '__main__': main() 

2.2 ImmutableDict的实现

ImmutableDict的实现如下:

from __future__ import print_function


def is_immutable(self): raise TypeError('%r objects are immutable' % self.__class__.__name__) class ImmutableDictMixin(object): """Makes a :class:`dict` immutable.  .. versionadded:: 0.5  :private:  """ _hash_cache = None @classmethod def fromkeys(cls, keys, value=None): instance = super(cls, cls).__new__(cls) instance.__init__(zip(keys, repeat(value))) return instance def __reduce_ex__(self, protocol): return type(self), (dict(self),) def _iter_hashitems(self): return iteritems(self) def __hash__(self): if self._hash_cache is not None: return self._hash_cache rv = self._hash_cache = hash(frozenset(self._iter_hashitems())) return rv def setdefault(self, key, default=None): is_immutable(self) def update(self, *args, **kwargs): is_immutable(self) def pop(self, key, default=None): is_immutable(self) def popitem(self): is_immutable(self) def __setitem__(self, key, value): is_immutable(self) def __delitem__(self, key): is_immutable(self) def clear(self): is_immutable(self) class ImmutableDict(ImmutableDictMixin, dict): """An immutable :class:`dict`.  .. versionadded:: 0.5  """ def __repr__(self): return '%s(%s)' % ( self.__class__.__name__, dict.__repr__(self), ) def copy(self): """Return a shallow mutable copy of this object. Keep in mind that  the standard library's :func:`copy` function is a no-op for this class  like for any other python immutable type (eg: :class:`tuple`).  """ return dict(self) def __copy__(self): return self

更多教程请关注微信公众号或者加Q群

==

猜你喜欢

转载自www.cnblogs.com/sunnyppl/p/8997309.html
今日推荐