PyH源码解析(5)steemCreated with Sketch.

in #cn6 years ago

检索子Tag对象或者内容

一个Tag对象如果有多个子Tag对象或者内容,那么怎么获得其中的某个子Tag对象或内容。如果Tag对象有ID,则使用其ID作为索引;如果没有设置ID,则使用Tag的名字作为ID,如果有多个相同名字的Tag,则其ID依次在后面增加上001、002、...。需要注意的是,则只是子Tag对象的索引ID,不是Tag对象的属性ID。如下面示例:

#例1:
>>> a=div(div(id='a1'))
>>> print(a.a1)
<div id="a1">
</div>

#例2:
>>> a=div(div('test'))
>>> print(a.div)
<div>
test
</div>

#例3:
>>> a=div(div('t1'),div('t2'))
>>> print(a.div_001)
<div>
t2
</div>

#例4:
>>> a=div('t1',div('a1'),'t2')
>>> print(a.content_001)
t2

以上例子可以看出,对于内容,则使用content作为索引。

实现原理

每一个Tag对象,都有一个id属性,这个ID就是其索引ID,用于其父节点进行索引。这个ID,默认是其ID属性值,如果没有设置ID属性,默认设置其Tag名字。每一个Tag对象id的计算都是由其父对象的setID函数计算并设置的,如下:

def setID(self, obj):#{{{
| 49 if isinstance(obj, Tag):
| 50 id = obj.id
| 51 n = len(
| 52 [t for t in self if isinstance(t, Tag) and t.id.startswith(id)])
| 53 else:
| 54 id = 'content'
| 55 n = len([t for t in self if not isinstance(t, Tag)])
| 56
| 57 if n:
| 58 id = '%s_%03i' % (id, n)
| 59 if isinstance(obj, Tag):
| 60 obj.id = id
| 61 return id

之后就很简单了,通过setattr函数,把子Tag对象的id属性添加到当前对象的属性中,这样父Tag对象就可以直接通过属性访问的方式来引用其子Tag对象和内容。