一、问题的背景

给定一组商品购买信息,找到商品购买中频繁出现的商品集。比如说,我们有如下的商品交易信息:

市场购物信息
Tip Items
1 Bread, Milk
2 Bread, Diaper, Beer, Egg
3 Milk, Diaper, Beer, Coke
4 Bread, Milk, Diaper, Beer
5 Bread, Milk, Diaper, Coke

我们定义,Itemset 为一系列item的集合,比如:{Milk, Bread, Diaper};定义 k-itemset 为包含k个items的itemset;定义support 是所有交易信息中,包含这个 itemset 的子集。比如s({Milk, Bread, Diaper}) = 2/5;定义frequent Itemset 是一组itemset,它的support 大于等于minsup,这个minsup值由我们自己给定。

为了找出频繁项集,最直观的方法是我们罗列出所有的候选项,然后计算每个候选项的support,最后将满足要求的频繁项保存下来。比如说,我们有M个交易信息储存在数据库中,有N个候选项,那么我们必须要比较MN次,显然它的时间复杂度是非常大的。一个有效的解决途径是我们使用有效的数据结构来存储候选项和交易信息,这样我们不需要将每个候选项与每个交易都匹配一次。

我们可以将候选集储存在哈希树中,这样我们不需要一个交易信息与每一个候选集进行比较,我们只需要比较那些哈希树中存在的候选集。

二、如何构建哈希树

假设我们有15个候选集,长度均为3:

{1 4 5}, {1 2 4}, {4 5 7}, {1 2 5}, {4 5 8}, {1 5 9}, {1 3 6}, {2 3 4}, {5 6 7}, {3 4 5}, {3 5 6}, {3 5 7}, {6 8 9}, {3 6 7}, {3 6 8}

我们需要:1、构建一个hash函数。 2、设定叶子的最大大小(每片叶子中能够存储的最大数据),如果某片叶子中的候选集数量超过了限制,我们需要对这个叶节点做分裂处理。

比如说我们构建了如下图所示的hash函数,在第一个层,对候选集的第一项进行判断,比如说我们对{1,2,5}进行判断,由于第一项为1,因此我们将它放到root的左节点。在第二层,我们对候选集的第二项进行判断,{1,2,5}的第二项是2,根据hash函数,我们再想中间走一步。在第三层,{1,2,5}的第三项是5,因此我们往中间走一步。当然,往下走一步仅在于你当前无法存储在3个节点的情况,因为我们定义了叶子的最大size是3,如果你这个节点能够存储下3个数据,那就没必要继续往下分裂了。

由此我们可以建立如下的哈希树:

那么给定一次商品交易信息,比如[1,2,3,5,6],我们应该如何将这次交易与候选项进行比较?根据hash函数,如果我们想左走,那么我们的选择一定是1开头,然后从[2,3,5,6]选择长度为2的子序列,继续往左走的话,由于[2,3,5,6]与哈希函数中的[1,4,7]无法找到共同项,因此往左走是行不通的,这样我们就避免了这次交易与候选集[1,4,5]的比较。同理我们往中间走,根据哈希函数得到了12[3,5,6]的集合,这样也就是有123,125,126三种可能性,因此与哈希树中对应叶节点的125,458,因此我们知道,在这次交易信息中,125这个候选集出现过一次。因此利用哈希树,我们避免了一部分的比较,减少了比较次数。

三、哈希树的Python实现

class Node:def __init__(self,val=[]):self.val = valself.children = {}class HashTree:def __init__(self):self.root = Node()#建立根节点def insert(self,val):#给定一个值val,创建一个值为val的节点并将其插入到树中root = self.rooti = 0while root.children:#if root has childrenif (val[i]-1) % 3 in root.children.keys():#如果想找的孩子存在root = root.children[(val[i]-1)%3]i += 1else:#if the child doesn't existroot.children[(val[i]-1)%3] = Node([val])return#so the root doesn't have childif len(root.val) < 3:#the value of root is smaller than 3root.val.append(val)returnelse:#root的值的个数已经等于3了,那么我们必须split rootroot.val.append(val)#先把val加入到root的值当中for item in root.val:#对于root值中的的每一项j = (item[i]-1) % 3#表示余数是多少if j in root.children.keys():#如果余数已经在其中了root.children[j].val.append(item)#将item加入到列表中else:root.children[j] = Node()#首先创建该节点root.children[j].val = [item]#如果没有,则创建新列表root.val = []                if len(root.children[j].val) == 4:#分裂节点后,仍然出现了大于3的情况,那么我们需要继续分裂节点i += 1root = root.children[j]for item in root.val:#对于root值中的的每一项j = (item[i]-1) % 3#表示余数是多少if j in root.children.keys():#如果余数已经在其中了                            root.children[j].val.append(item)#将item加入到列表中else: root.children[j] = Node()root.children[j].val = [item]#如果没有,则创建新列表root.val = []def PrintTree(self,node):#如何 层次的输出树if not node.val:#如果这个节点的值不存在if not node.children: return#如果孩子也没有else:#有孩子了res = []for item in node.children.values():res += [self.PrintTree(item)]else:#这个节点的值存在return node.valreturn resobj = HashTree()
values = '[{1 2 4}, {1 2 9}, {1 3 5}, {1 3 9}, {1 4 7}, {1 5 8}, {1 6 7}, {1 7 9}, {1 8 9}, {2 3 5}, {2 4 7}, {2 5 6}, {2 5 7}, {2 5 8}, {2 6 7}, {2 6 8}, {2 6 9}, {2 7 8}, {3 4 5}, {3 4 7}, {3 5 7}, {3 5 8}, {3 6 8}, {3 7 9}, {3 8 9}, {4 5 7}, {4 5 8}, {4 6 7}, {4 6 9}, {4 7 8}, {5 6 7}, {5 7 9}, {5 8 9}, {6 7 8}, {6 7 9}]'
values = values.replace('{','[').replace('}',']').replace(' ',',').replace(',,',',')
values = 'values = ' + valuesexec(values)for item in values:obj.insert(item)print(obj.PrintTree(obj.root))

哈希树的python实现相关推荐

  1. 图文详解哈希树-Merkle Tree(默克尔树)算法解析

    2019独角兽企业重金招聘Python工程师标准>>> Merkle Tree概念   Merkle Tree,通常也被称作Hash Tree,顾名思义,就是存储hash值的一棵树. ...

  2. HashTree(哈希树) ——和trie类似,只是将字符换成了质数,sphinx用到了???...

    摘自:http://blog.csdn.net/yang_yulei/article/details/46337405 哈希树的理论基础 [质数分辨定理] 简单地说就是:n个不同的质数可以" ...

  3. C - 数据结构实验之查找三:树的种类统计(哈希树)

    Description 随着卫星成像技术的应用,自然资源研究机构可以识别每一个棵树的种类.请编写程序帮助研究人员统计每种树的数量,计算每种树占总数的百分比. Input 输入一组测试数据.数据的第1行 ...

  4. HDU - 5658 CA Loves Palindromic(回文自动机/哈希+树状数组)

    题目链接:点击查看 题目大意:给出一个字符串 s ,接下来给出 m 个查询,每次查询的形式会给出一个 l 和 r ,问区间 [ l , r ] 内有多少个本质不同的回文子串 题目分析:因为查询的次数比 ...

  5. 012-数据结构-树形结构-哈希树[hashtree]、字典树[trietree]、后缀树

    一.哈希树概述 1.1..其他树背景 二叉排序树,平衡二叉树,红黑树等二叉排序树.在大数据量时树高很深,我们不断向下找寻值时会比较很多次.二叉排序树自身是有顺序结构的,每个结点除最小结点和最大结点外都 ...

  6. 智慧树python程序设计答案_智慧树知道Python程序设计完整答案

    智慧树知道Python程序设计完整答案 更多相关问题 已知函数f(x)=a(1-2|x-12|),a为常数且a>0.(1)f(x)的图象关于直线x=12对称:(2)若x0满足f(f(x0))=x ...

  7. B+树的python实现

    B+树的python实现 本代码来自极客学院网站死里逃生2018年发表的blog关于 B+tree (附 python 模拟代码).该代码实现了B+树的插入.删除.范围查找,功能完善,但也存在诸多问题 ...

  8. python交互式程序设计导论第一周答案_智慧树知到Python程序设计基础见面课测试答案...

    智慧树知到Python程序设计基础见面课测试答案 更多相关问题 [多选题]用TLC法检查药物中杂质时,通常有以下几种方法 [判断题]月氏从故地到迁入地,均在丝绸之路沿线 [单选题]若炽灼残渣留做重金属 ...

  9. LeetCode刷题——哈希表(python语言)

    LeetCode刷题--哈希表(python语言) 一.哈希表 1.1 哈希表的概念 哈希表,也叫散列表.其实可以很像python的字典,也就是键(key)值(Hash(key))对,最简单也最常用的 ...

最新文章

  1. JIT Compiler编译器及指令集
  2. R语言使用str_order函数和str_sort函数对字符向量进行排序(str_order返回字符串排序的次序值(索引)、str_sort返回排序后的字符串)
  3. dropdownlist javascript 取得value text
  4. 成对的歌曲,其总持续时间可被60整除
  5. java mysql实现原理_MySQL事务实现原理
  6. 国开本科计算机应用基础操作题,2019秋国开大学计算机应用基础Windows7操作系统形考题目及答案...
  7. extjs4动态生成多表头
  8. Ubunbu新建的用户使用SecureCrt无法Table补全、无法高亮
  9. Windows Xp 优化文件 的一段BAT代码
  10. 利用计算机制作图表,利用Excel进行数据分组和制作统计图表.doc
  11. 调试经验——Windows10中iTunes不能识别iPad的解决方法
  12. 建筑工地施工现场人员安全管理软件系统
  13. Alpha通道及合成运算
  14. AlignedReID
  15. python高级教程_Python高级进阶教程
  16. ubuntu20.04安装matlab2018b
  17. Apache Structured Streaming_JZZ158_MBY
  18. 白鹭引擎开发微信小游戏进阶教程文档
  19. 宠物诊所java项目_JavaWeb项目-宠物诊所管理系统
  20. zeppelin源码分析(1)——编译、调试和maven modules分析

热门文章

  1. Mac应用程序无法打开或文件损坏的处理方法,Mac任何来源开启教程
  2. Cocos2d-x :什么是锚点?(简单点说:锚点就是图片的原点)
  3. Golang数据库编程(MySQL)
  4. Android 12.0 SystemUI状态栏屏蔽掉通知栏不显示通知
  5. 一起看看这些大厂面试真题查漏补缺吧,专题解析
  6. Acwing 77场
  7. 前后端角度看接口(什么是json)?
  8. 对于第一阶段学习的总结
  9. 推荐系统的常见推荐算法的性能比较
  10. [图神经网络]ViG(Vision GNN)网络代码实现