序列的去重

对所获取的的数据进行去重显得尤为重要,爬虫获取的冗余数据在大多时候都是都是无效且占用空间的.

设想有两个场景,一个是去除序列中出现的重复元素,获得的新序列是无序的,另外一个是去重获得新序列之后,依然是按照处理之前的顺序进行排列的.

无论是哪两种情况,序列的去重都是围绕set集合展开的,当然这也是set比较重要的属性.

对于第一种情况,直接使用set来处理就尤为简单

1
2
3
a = [1,3,2,1,4,3]
a = set(a)
a = list(a)
1
[1, 2, 3, 4]

可以看到输出的结果并不是按照原始顺序排列的,但依然有个问题就是转换后序列是按照升序排列的,最后测试一下,发现数据量较大时是不会出现这种情况的,集合并没有自动排序的功能.

对于第二种情况,想要去重并且顺序不发生改变,这里又有两种情况,一种是序列元素是可哈希的,另外一种是序列元素不可哈希的.

可哈希对象表示的是,在它生存期内是不可变的,如整数,浮点数,字符串,元组等.

对于可哈希元素:

1
2
3
4
5
6
7
8
a = [1,3,2,1,4,5]
def judge(items):
seen = set()
for item in items:
if item not in seen:
yield item
seen.add(item)
b = list(judge(a))
1
[1, 3, 2, 4, 5]

使用这种方法,可以实现不打乱顺序产生序列.

对于不可哈希元素:

1
2
3
4
5
6
7
8
9
a = [{'x':1, 'y':2}, {'x':1, 'y':3}, {'x':1, 'y':2}]
def judge(items, key=None):
seen = set()
for item in items:
val = item if key is None else key(item)
if val not in seen:
yield item
seen.add(val)
b = list(judge(a, key = lambda key:(key['x'], key['y'])))
1
[{'x': 1, 'y': 2}]

如果容器中的元素为不可哈希元素时,需要使用这种方法来进行去重才能保证保持元素的顺序,这种方法同时也可以实现容器中元素为可哈希的情况.