#参考Link:https://www.jianshu.com/p/2ee0a247a8cc
#创建一个数据集合
def loadDataSet():
#return [[1,3,4],[2,3,5],[1,2,3,5],[2,5]]
return apriori_metadata
# 创建一项集
# 所有元素转换为不可变的字典,放到列表中
def createC1(dataSet):
c1 = []
for trans in dataSet:
for item in trans:
if not [item] in c1:
c1.append([item])
c1.sort()
# [1,2,3,4,5]
return list(map(frozenset,c1)) #[{1},{2},{3},{4},{5}]
# 获取满足最小支持度的候选集与其支持度
# 过滤掉不符合支持度的集合
# 返回 频繁项集列表retList 所有元素的支持度字典
# D = [{1, 3, 4}, {2, 3, 5}, {1, 2, 3, 5}, {2, 5}]
# Ck 是k项集 example:1-项集 [{1},{2},{3},{4},{5}]
# minSupport最小支持度
def getSetAndSupport(D, Ck, minSupport):
subSetSupportNum = {}
for tid in D:
for oneOfCk in Ck: #取出k-项集 中一项
if oneOfCk.issubset(tid): # 判断can是否是tid的《子集》 (这里使用子集的方式来判断两者的关系)
if oneOfCk not in subSetSupportNum: # 统计该值在整个记录中满足子集的次数(以字典的形式记录,frozenset为键)
subSetSupportNum[oneOfCk] = 1
else:
subSetSupportNum[oneOfCk] += 1
#之前是对每一个 集合进行计数 用于计算支持度
numItems = float(len(D)) # 获取事务数目
retList = [] # 重新记录满足条件的数据值(即支持度大于阈值的数据)
supportData = {} # 每个数据值的支持度
for subSet in subSetSupportNum:
support = subSetSupportNum[subSet] / numItems
if support >= minSupport: # 只是将满足最小支持度的项集插入
retList.insert(0, subSet)
supportData[subSet] = support
return retList, supportData # 排除不符合支持度元素后的元素 每个元素支持度
# 连接与剪枝
# 生成所有可以组合的集合
# 频繁项集列表Lk 项集元素个数k [frozenset({2, 3}), frozenset({3, 5})] -> [frozenset({2, 3, 5})]
# Lk 是k项集
# linkCK和cutCK都其实是K+1项候选 只是为了方便写成linkCK和cutCK
def aprioriGen(Lk, k,supportData,minSupport = 0.06):
Ck_1 = []
linkCK = {}
cutCK = []
lenLk = len(Lk)
#连接
for i in range(lenLk): # 两层循环比较Lk中的每个元素与其它元素
for j in range(i+1, lenLk):
#****连接操作****
Ck_1.append(Lk[i] | Lk[j]) # 求并集
linkCK = set(Ck_1) # 去除Ck_1中相同的集合
linkCK = list(linkCK)
#剪枝
for oneOfCk in linkCK: # 两层循环判断 连接后的集合列表
flag = 1
for sup in supportData:
if supportData[sup] < minSupport:
if sup.issubset(oneOfCk):
flag = 0
if flag == 1:
cutCK.append(oneOfCk)
#print(cutCK)
return cutCK # 返回频繁项集列表Ck
# 封装所有步骤的函数
# 返回 所有满足大于阈值的组合 集合支持度列表
def apriori(dataSet, minSupport = 0.06):
Data = list(map(set, dataSet)) # 转换列表记录为字典 [{1, 3, 4}, {2, 3, 5}, {1, 2, 3, 5}, {2, 5}]
C1 = createC1(dataSet) # 将每个元素转会为frozenset字典
# [frozenset({1}), frozenset({2}), frozenset({3}), frozenset({4}), frozenset({5})]
supportAll = [] # supportAll 用于保存所有的支持度 用supportData 保存k-项集的支持度
# supportData在aprioriGen的剪枝操作中时候会用到
L1, supportData = getSetAndSupport(Data, C1, minSupport) # 过滤数据 获取1-项集 和其对应的支持度
supportAll.append(supportData) #将1-项集加入到支持度的列表中
L = [L1] # L 会存储所有的的项集
k = 0
while (len(L[k]) > 0): # 若仍有满足支持度的集合则继续做关联分析
print(k,end='\n')
Ck = aprioriGen(L[k], k, supportData) # Ck候选频繁项集
Lk, supportData = getSetAndSupport(Data, Ck, minSupport) # Lk频繁项集
#supportData.update(supK) # 更新字典(把新出现的集合:支持度加入到supportData中)
supportAll.append(supportData)
L.append(Lk) # 将Lk 放到 L 列表中
k += 1 # 每次新组合的元素都只增加了一个,所以k也+1(k表示元素个数)
return L, supportAll
#获取到数据集合
dataSet = loadDataSet()
#Apriori算法 所有满足大于阈值的组合 集合支持度列表
L,suppAll = apriori(dataSet)
for lk in L:
print(lk)
print()
#打印出所有支持度
for supp in suppAll:
for sup in supp:
print(sup,supp[sup])
来源:CSDN
作者:Jxufe渣渣斯
链接:https://blog.csdn.net/JxufeCarol/article/details/104001596