在利用Apriori算法计算关联规则时由于涉及到遍历搜索在计算数据较大时复杂度高,本文主要是在网上现有的python code中进行修改使计算速度提升100倍。总数据集为700多万条,频繁项集K=5
1,关联规则需根据用户需求进行K维pair对进行交叉,在第一轮迭代后删除支持度<最小支持度的数
#L1 为第一轮迭代后符合最小支持度的项集 #data_set为原始数据集 new_l1 = [] for p in L1: new_l1.extend(list(p)) data_set2 = [] for t in data_set: new_t = [s for s in t if s in new_l1] if len(new_t)>=5: data_set2.append(new_t)
第一步进行数据删除后在本例中删除20%数据(最小支持度选择较小,因此删除数据不多)
2,计算复杂度最高的一点是需要每一行循环,并对所有符合交叉条件的项集进行循环来计算各个项集的频繁项。本例中当K=2时循环次数是700W*3400。根据数据特点(每一行数据个数均值为10条),当k<=4时每一次的迭代时先计算这一行数据所有可能的交叉方式,然后检验交叉项集是否为频繁项集,可将循环次数降为700W*45.
Lk = set() item_count = {} for t in data_set: if k==1: tmp = set() for item in t: item_set = frozenset([item]) tmp.add(item_set) elif k<=4: tmp = combine(t, k) else: tmp = Ck.copy() for item in tmp: if item in Ck and item.issubset(t): if item not in item_count: item_count[item] = 1 else: item_count[item] += 1
def combine(l, n): l.sort() answers = [] one = [0] * n def next_c(li = 0, ni = 0): if ni == n: answers.append(copy.copy(one)) return for lj in xrange(li, len(l)): one[ni] = l[lj] next_c(lj + 1, ni + 1) next_c() tmp =set() for i in answers: tmp.add(frozenset(i)) return tmp
做完上述两步速度提升100倍。