tornado架构分析3 options.py中基础类_Option

1 数据清洗

option里面最重要的方法就是parse,在这里,parse函数的一开始就调用了后面的子函数_parse_datetime,_parse_timedelta,_parse_bool,_parse_string。经过我分割,查找具体函数执行情况,这四个函数其实是清理格式的,为了防止格式混乱,导致后期处理困难。就用它们做了格式清洗。

1     def parse(self, value):
2         _parse = {
3             datetime.datetime: self._parse_datetime,
4             datetime.timedelta: self._parse_timedelta,
5             bool: self._parse_bool,
6             basestring_type: self._parse_string,
7         }.get(self.type, self.type)
8 
9 注:parse函数的部分内容

(1)时间格式数据清洗

 1     # Supported date/time formats in our options
 2     _DATETIME_FORMATS = [
 3         "%a %b %d %H:%M:%S %Y",
 4         "%Y-%m-%d %H:%M:%S",
 5         "%Y-%m-%d %H:%M",
 6         "%Y-%m-%dT%H:%M",
 7         "%Y%m%d %H:%M:%S",
 8         "%Y%m%d %H:%M",
 9         "%Y-%m-%d",
10         "%Y%m%d",
11         "%H:%M:%S",
12         "%H:%M",
13     ]
14 
15     def _parse_datetime(self, value):
16         for format in self._DATETIME_FORMATS:
17             try:
18                 return datetime.datetime.strptime(value, format)
19             except ValueError:
20                 pass
21         raise Error('Unrecognized date/time format: %r' % value)

这个列表是有讲究的,从列表顺序自上而下进行匹配。

当匹配成功后,就返回一个标准值。如果匹配失败,就返回一个ValueError。因此,原作者在这里对ValueError做了一个异常处理。

如果全部都匹配失败,那么久返回一个错误,证明时间参数的确有问题了。

以下部分是我做的一个匹配失败报错的情况:

1 >>> datetime.datetime.strptime("19:20:20", "%H:%M")
2 Traceback (most recent call last):
3   File "<stdin>", line 1, in <module>
4   File "C:Python27lib\_strptime.py", line 328, in _strptime
5     data_string[found.end():])
6 ValueError: unconverted data remains: :20

(2) unix时间模式的数据清洗

我们都知道,程序中表示时间还有一种方式是unix时间戳,大意就是从1970年开始,已经执行的秒数。

这部分,我没有细看,不过简单分析,应该就是时间模式的一个替换

 1     _TIMEDELTA_ABBREV_DICT = {
 2         'h': 'hours',
 3         'm': 'minutes',
 4         'min': 'minutes',
 5         's': 'seconds',
 6         'sec': 'seconds',
 7         'ms': 'milliseconds',
 8         'us': 'microseconds',
 9         'd': 'days',
10         'w': 'weeks',
11     }
12 
13     _FLOAT_PATTERN = r'[-+]?(?:d+(?:.d*)?|.d+)(?:[eE][-+]?d+)?'
14 
15     _TIMEDELTA_PATTERN = re.compile(
16         r's*(%s)s*(w*)s*' % _FLOAT_PATTERN, re.IGNORECASE)
17 
18     def _parse_timedelta(self, value):
19         try:
20             sum = datetime.timedelta()
21             start = 0
22             while start < len(value):
23                 m = self._TIMEDELTA_PATTERN.match(value, start)
24                 if not m:
25                     raise Exception()
26                 num = float(m.group(1))
27                 units = m.group(2) or 'seconds'
28                 units = self._TIMEDELTA_ABBREV_DICT.get(units, units)
29                 sum += datetime.timedelta(**{units: num})
30                 start = m.end()
31             return sum
32         except Exception:
33             raise

(3)  bool值的数据清洗

这部分是用一个判断来做的,根据判断结果,自然而然就将不规范的bool值(如true,false)转成规范的bool值了

这里函数我提取出来并测试了一下,是成功的,但是我没有搞明白实际的原理。

1     def _parse_bool(self, value):
2         return value.lower() not in ("false", "0", "f")

(4)  字符串变量的数据清洗

这部分就没啥好说的了,大意就是把str等都转成unicode

1     def _parse_string(self, value):
2         return _unicode(value)
原文地址:https://www.cnblogs.com/fxdjjn/p/8421121.html