【Python机器学习】Apriori算法——使用APriori算法来发现频繁集

news2025/1/12 12:06:16

关联分析的目标包括两项:发现频繁项集和发现关联规则。首先需要找到频繁项集,然后才能获得关联规则。

APriori算法时发现频繁项集的一种方法。APriori算法的两个输入参数是最小支持度和数据集,算法首先会生成所有单个物品的项集列表;接着扫描交易记录来查看哪些项集满足最小支持度要求,那些不满足最小支持度的集合将会被去掉;然后,对剩下来的集合进行组合以生成包含两个元素的项集;接下来,再重新扫描交易记录,去掉不满足最小支持度的项集。该过程重复到所有项集都被去掉。

生成候选项集

在使用Python来对整个程序编码之前,需要创建一些辅助函数。下面创建一个用于构建初始集合的函数,也会常见一个通过扫描数据集以寻找交易记录子集的函数。数据集扫描的伪代码大致如下:

对数据集中的每条交易记录tran:

对每个候选项集can:

    检查一下can是否是tran的自己:

        如果是,则增加can的计数值

    对每个候选项集:

    如果其支持度不低于最小值,则保留该项集

    返回所有频繁项列表

实际代码实现:

def loadData():
    return [[1,3,4],[2,3,5],[1,2,3,5],[2,5]]
#构建集合C1。C1是大小为1的所有候选项集的集合。
def createC1(dataSet):
    C1=[]
    for transaction in dataSet:
        for item in transaction:
            if not [item] in C1:
                C1.append([item])
    C1.sort()
    #对C1中每个项构建一个不变集合
    return list(map(frozenset,C1))
def scanD(D,Ck,minSupport):
    ssCnt={}
    for tid in D:
        for can in Ck:
            if can.issubset(tid):
                if not can in ssCnt:
                    ssCnt[can]=1
                else:
                    ssCnt[can]=ssCnt[can]+1
    numItems=float(len(D))
    retList=[]
    supportData={}
    for key in ssCnt:
        support=ssCnt[key]/numItems
        if support>=minSupport:
            retList.insert(0,key)
        supportData[key]=support
    return retList,supportData

上述代码包含了3个函数,其中第一个函数loadDataSet()创建了一个用于测试的简单数据集。

createC1()函数将构建集合C1。C1是大小为1的所有候选集的集合。APriori算法首先构建集合C1,然后扫描数据集来判断这些只有一个元素的项集是否满足最小支持度的要求。那些满足最低要求的项集构成项集L1,而L1中的元素相互组合构成C2,C2再进一步过滤变为L2,以此类推。

因此算法需要一个createC1()函数开构建第一个候选项集的列表C1。由于算法一开始是从输入数据中提取候选项集列表,所以这里需要一个特殊的函数来处理,而后续的项集列表则是按一定的格式存放的。

首先创建一个空列表C1,它用来存储所有不重复的项值。接下来遍历数据集中的所有交易记录。对每一条记录,遍历记录中的每一个项。如果某个物品项没有在C1中出现,则将其添加到C1中。这里并不是简单地添加每个物品项,而是添加只包含该物品项的一个列表。这样做的目的是为每个物品项构建一个集合。

因为在APriori算法的后续处理中,需要做集合操作。Python不能创建只有一个整数的集合,因此这里必须使用列表。

这就是我们使用一个由单物品列表组成的大列表的原因。最后,对大列表进行排序并将其中的每个单元素列表映射到frozenset(),最后返回frozenset的列表。

下一个函数是scanD(),它有三个参数:数据集、候选项集列表Ck以及感兴趣项集的最小支持度minSupport。该函数用于从C1生成L1。另外,该函数会返回一个包含支持度值的字典以备后用。scanD()函数首先创建一个空字典ssCnt,然后遍历数据集中的所有交易记录已经C1中的所有候选集。如果C1中的集合是记录的一部分,那么增加字典中对应的计数值。这里字典的键就是集合。当扫描完数据集中的所有项以及所有的候选集时,就需要计算支持度。不满足最小支持度要求的集合不会输出。函数也会先构建一个空列表,该列表包含满足最小支持度要求的集合。下一个循环遍历字典中的每个元素并且计算支持度。如果支持度满足最小支持度要求,则将字典元素添加到retList中。可以使用语句 retList.insert(0,key) 在列表的首部插入任意新的集合。函数最后返回最频繁项集的支持度supportData。

实际运行效果:

dataSet=loadData()
C1=createC1(dataSet)
print('C1:',C1)

D=list(map(set,dataSet))
print(D)

L1,suppData0=scanD(D,C1,0.5)
print(L1)

上图最后一行中的4个项集构成了L1列表,该列表中的每个单物品项集至少出现在50%以上的记录中。由于物品4没有达到最小支持度要求,所以没有包含在L1中。通过去掉这件物品,减少了查找两物品项的工作量。

组织完整的APriori算法

整个APriori算法的伪代码如下:

当集合中项的个数大于0时

    构建一个k个项组成的候选项集的列表

    检查数据以确认每个项集都是频繁的

    保留频繁项集并构建k+1项组成的候选项集的列表

既然可以过滤集合,那么就能够构建完整的APriori算法了:

def aprioriGen(Lk,k):
    retList=[]
    lenLk=len(Lk)
    for i in range(lenLk):
        for j in range(i+1,lenLk):
            L1=list(Lk[i])[:k-2]
            L2=list(Lk[j])[:k-2]
            L1.sort()
            L2.sort()
            if L1==L2:
                retList.append(Lk[i]|Lk[j])
    return retList
def apriori(dataSet,minSupport=0.5):
    C1=createC1(dataSet)
    D=list(map(set,dataSet))
    L1,supportData=scanD(D,C1,minSupport)
    L=[L1]
    k=2
    while (len(L[k-2])>0):
        Ck=aprioriGen(L[k-2],k)
        Lk,supK=scanD(D,Ck,minSupport)
        supportData.update(supK)
        L.append(Lk)
        k=k+1
    return L,supportData

上述代码中有两个函数,其中主函数是apriori(),它会调用aprioriGen()来创建候选集项Ck。

函数aprioriGen()的输入参数为频繁项集列表Lk与项集元素个数k,输出为Ck。举例来说,该函数以{0}、{1}、{2}作为输入,会生成{0,1}、{0,2}、{1,2}。要完成这一点,首先创建一个空列表,然后计算Lk中的元素数目。接下来,比较Lk中的每一个元素与其他元素,这可以通过两个for循环来实现。接着,取列表中的两个集合进行比较,如果这两个列表的前面k-2个元素都相同,那么就将这两个集合合成一个大小为k的集合。这里使用集合的并操作来完成。

上面的操作被封装在apriori()函数中。给该函数传递一个数据集以及一个支持度,函数会生成候选项集的列表,这通过首先创建C1然后读入数据集将其转换为D(集合列表)来完成。程序中使用map列表将set()映射到dataSet列表中的每一项。接下来利用scanD()函数来创建L1,并将L1放入列表L中。L会包含:L1、L2、L3……。现在有了L1,后面会继续找L2、L3……,这可以通过while循环完成,它创建包含更大项集的更大列表,直到下一个大的项集为空。

之后首先使用aprioriGen()来创建Ck,然后使用scanD()基于C看来创建Lk。Ck是一个候选项集列表,然后scanD()会变量Ck,丢掉不满足最小支持度要求的项集。Lk列表被添加到L,同时增加k的值,重复上述过程。最后,当Lk为空时,程序返回L并退出。

代码运行效果:

dataSet=loadData()
L,suppData=apriori(dataSet)
print(L)

再尝试一下70%的支持度要求:

dataSet=loadData()
L,suppData=apriori(dataSet,minSupport=0.7)
print(L)

变量suppData是一个字典,它包含我们项集的支持度值。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2040122.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【源码】Sharding-JDBC源码分析之Yaml分片配置原理(二)

Sharding-JDBC系列 1、Sharding-JDBC分库分表的基本使用 2、Sharding-JDBC分库分表之SpringBoot分片策略 3、Sharding-JDBC分库分表之SpringBoot主从配置 4、SpringBoot集成Sharding-JDBC-5.3.0分库分表 5、SpringBoot集成Sharding-JDBC-5.3.0实现按月动态建表分表 6、【…

奥运奖牌窥视

1 前言 2024巴黎奥运会已经闭幕了,中国队创纪录地获得了海外举办的奥运会的最佳成绩,我们来个管中窥豹,看看中国队从哪些项目中取得了奖牌。 2 奖牌组成 游泳真是大项,小项数量众多,比如个人自由泳就有100m、200m、4…

经纬恒润亮相第四届焉知汽车年会,功能安全赋能域控

8月初,第四届焉知汽车年会在上海举行。此次年会围绕当下智能电动汽车的热点和焦点,聚焦于智能汽车场景应用、车载通信、激光雷达、智能座舱、功能安全、电驱动系统等多个领域,汇聚了来自OEM、科技公司、零部件供应商、测试认证机构、政府院校…

顾客账单管理和台账-SAAS 本地化及未来之窗行业应用跨平台架构

一、客户账单对客户和企业的帮助 为您的企业客户打造便捷新体验!现在,企业客户做账消费后,可自行下载账单。这一创新举措不仅大大减少了公司售后的压力,更能助力企业客户提升办公效率。想象一下,无需繁琐的沟通与等待…

论文阅读:一种基于凸规划的高效有向最密子图发现方法 | SIGMOD 2022

论文概述 这篇论文的主题是研究如何在有向图中找到密度最高的子图,这个问题被称为有向最密子图(Directed Densest Subgraph, DDS)问题。该问题在许多应用中非常重要,如社交网络分析、社区发现、假粉丝检测等。论文提出了一种基于…

【前端面试】挖掘做过的nextJS项目(上)

为什么使用nextJS 需求: 快速搭建宣传官网 1.适应pc、移动端 2.基本的路由跳转 3.页面渲染优化 4.宣传的图片、视频资源的加载优化 5.seo优化 全栈react web应用、 tailwind css原子工具的支持,方便书写响应式ui app router(React 服务器组件)支持服务器渲…

灵活易用的树莓派相机和计算机,降低了3D冰川建模的成本!

利兹大学的研究人员正在监测秘鲁的凯尔卡亚冰帽,这是世界上仅有的几个热带冰帽之一。 在欧洲成功进行试验之后,利兹大学地理学院​​​​​​​的研究人员正在安第斯山脉和喜马拉雅山脉使用树莓派计算机和树莓派高品质相机,建立低成本、长期…

Springboot权限管理系统

1、基于SpringBoot Mybatis Plus SaToken Thymeleaf Layui的后台管理系统 2、接入Sa-Token,支持菜单权限 数据库支持 MySQL、Oracle、sqlServer 等主流数据库 3、提供代码生成器,基本增删改查无需编写,可快速完成开发任务。 4、后台接口R…

从行为面试问题(behavioral questions)看中美程序员差异。

中美程序员在职场中的工作状态和职能、福利等有很大区别,从面试中的BQ轮就可见一斑。 中美程序员的面试轮差异? 国内的面试轮在不同公司间差异很大,但总体的问题类型包含笔试面试(算法题、概念题、项目深挖、职业目标、职场文化…

Leetcode JAVA刷刷站(27)移除元素

一、题目概述 二、思路方向 为了解决这个问题,你可以使用双指针的方法来原地移除所有等于 val 的元素,并返回不等于 val 的元素数量。 三、代码实现 public class Solution { public int removeElement(int[] nums, int val) { int left 0; // 左指…

结构开发笔记(四):solidworks软件(三):绘制36x36方块摄像头示意体

若该文为原创文章,转载请注明原文出处 本文章博客地址:https://hpzwl.blog.csdn.net/article/details/141187797 长沙红胖子Qt(长沙创微智科)博文大全:开发技术集合(包含Qt实用技术、树莓派、三维、OpenCV…

【中国数据库前世今生】数据存储管理的起源与现代数据库发展启蒙

记录开启本篇的目的: 作为1名练习时长2年半的DBA,工作大部分时间都在和数据库打交道,包括Oracle,Mysql,Postgresql,Opengauss等国内外数据库。但是对数据库的发展史却知之甚少。 正好腾讯云开发者社区正在热播:【纪录片】中国数据库前世今生,借此机会了解…

C语言 | Leetcode C语言题解之第337题打家劫舍III

题目: 题解: struct SubtreeStatus {int selected;int notSelected; };struct SubtreeStatus dfs(struct TreeNode *node) {if (!node) {return (struct SubtreeStatus){0, 0};}struct SubtreeStatus l dfs(node->left);struct SubtreeStatus r df…

ubuntu22.04不生成core文件

一、检查服务器的core文件是否打开 ulimit -a //查看时候打开core 如果core file size 是0就是关闭的!服务一般都是关闭的!将他打开即可! ulimit -c size//设置core file的大小,自定义 此时打开就可以生成了core文件了&#xff…

C语言 | Leetcode C语言题解之第336题回文对

题目&#xff1a; 题解&#xff1a; #define SIZE 9470 #define N 168000 #define P 13331typedef unsigned long long ULL; ULL p[301];//p[i]存储P^ivoid init()//初始化p进制次幂数组 {int i;p[0]1;for(i1;i<300;i){p[i]p[i-1]*P;} }int** palindromePairs(char**words,…

node异常:npm ERR! gyp verb check python checking Python executable “python2“ in t

node异常:npm ERR! gyp verb check python checking Python executable "python2" in t node异常&#xff1a; npm ERR! gyp verb check python checking for Python executable "python2" in t降低版本&#xff1a;npm install -g npm6.14.4 欢迎关注&a…

设计模式六大原则(一)--单一职责原则

GPT-4o (OpenAI) 单一职责原则&#xff08;Single Responsibility Principle&#xff0c;SRP&#xff09;是面向对象设计中的一条基本原则。该原则的核心思想是&#xff1a;一个类应该只有一个引起它变化的原因。换句话说&#xff0c;一个类应该只有一个职责&#xff08;即一个…

【嵌入式操作系统(Linux篇)】知识点期末复习(2)

以下是关于嵌入式操作系统&#xff08;Linux篇&#xff09;的知识点总结版 目录 ​ part 1 Linux系统基础 1、嵌入式OS(EOS): 2、嵌入式操作系统的特点 3、嵌入式Linnx的优势 4、Linnx是什么&#xff1f;是一种UNIX操作系统的克隆 5、Linux操作系统整体介绍. (1)Lin…

智能外呼机器人助力电销

在接回一家公司的电话时&#xff0c;听着员工那动听的声音&#xff0c;你或许会猜到电话那头是个清纯美丽的女孩&#xff0c;其实&#xff0c;打电话给你的只是一个机器人。外呼智能机器人开启了智能人机交互时代。 1、情绪稳定 每个电话都可以用最佳的声音和答案与客户进行沟…

SpringBoot响应式编程(2)WebFlux入门

一、概述 1.1简介 简单来说&#xff0c;Webflux 是响应式编程的框架&#xff0c;与其对等的概念是 SpringMVC。两者的不同之处在于 Webflux 框架是异步非阻塞的&#xff0c;其可以通过较少的线程处理高并发请求。 WebFlux&#xff1a;底层完全基于nettyreactorspringweb 完成…