精华内容
下载资源
问答
  • 提升
    千次阅读 多人点赞
    2020-11-05 10:05:30

    整型提升

    什么是整型提升?

    首先,我们应该知道这一点:C语言中整型运算总是至少缺省整型类型的精度来进行的。

    这句话什么意思呢?用大白话说就是:C语言中字节数少于整型字节数的数据类型在进行整型运算时,该类型的数据会被默认转为整型数据。

    其中,该类型的数据被转化为整型数据的过程就称为整型提升

    为什么要进行整型提升?

    为什么会发生整型提升呢?这是由计算机体系结构决定的,我们都知道计算机中的计算都由CPU完成,具体来说是由CPU中的运算器(ALU)完成的。而ALU一般在被设计时,其操作对象——操作数的字节大小被要求至少是int的字节数。此时,我们还要明晰一个事情,那就是数据在被运算时,数据并不是直接在ALU上存储的,而是存储在CPU的寄存器(register)中,而通用寄存器的字节大小与ALU操作数的字节大小保持一致。

    这又怎样?空间大又不是不能存储字节数少的数据。是的,话没错,能存,但问题在于我是4个字节的空间(大房间里有四个小房子),你是少于4个字节的数据(不能完全占据整个大房间),我到底该把你安排在哪个小房间里?我把你随便放进去的话,我要用你时又要在4个小房间里查找你到底在哪些房间里,这样势必会让我的效率变低。所以,你在住进来时,不好意思,你至少得把自己变成4个字节的,我再把你直接放进去,用你时我也不用查你在哪,我找到大房间就找到了你。

    可能这会有人会问,那我多于4个字节怎么办?不要担心,你多于4个字节,大不了我给你再安排一间大房子,你一个人住两间总该够了。在64位平台,C语言非自定义数据类型的字节数只有4种(1,2,4,8)。两间大房子妥妥把你舒舒服服住好喽!

    再看非自定义数据类型的字节数取值可能,我们发现只有(1,2)在进行整型运算时,会发生整型提升。而这两个数据类型对应的便是charshort

    说来说去,我们一句话就可以给它总结了:C语言中,表达式中的字符和短整型操作数在使用之前会发生整形提升,变为普通整型

    再来回顾一下问题:为什么要进行整型提升?这是由计算机体系结构决定的!

    怎么进行整型提升?

    大白话:怎么将少于4个字节的数据变成4个字节的数据?

    规则!规则!规则!:整型提升是按照变量的类型来进行提升的。具体点如下:

    a. 如果是无符号数,则高位直接补0;
    b. 如果是有符号数,则高位全补符号位。
    

    对!你没有看错,我也没有说错,就这么两句话!

    举个栗子:

    声明一点:任何数据在计算机中进行存储时,都是它的二进制形态,再精确点就是以补码形态进行存储。

    char c = -1;
    

    c变量的空间里存储着-1的补码(1111 1111),因为char只有一个字节,所以仅有8个比特位。
    这个char定义时没说unsigned char吧?所以此char有符号char.
    那它在进行整型提升时,用规则b。(1111 1111)被char修饰为有符号数,所以它的最高位为符号位!符号位为1,则它进行整型提升时,高位补3个字节的1。
    即(1111 1111 1111 1111 1111 1111 1111 1111

    再来看第二个栗子:

    char c = 1;
    

    c变量的空间里存储着1的补码(0000 0001),因为char只有一个字节,所以仅有8个比特位。
    这个char定义时没说unsigned char吧?所以此char有符号char.
    那它在进行整型提升时,用规则b。(0000 0001)被char修饰为有符号数,所以它的最高位为符号位!符号位为0,则它进行整型提升时,高位补3个字节的0。
    那我对你进行整型提升时,高位补2个字节的0就就行了。
    即(0000 0000 0000 0000 0000 0000 0000 0001

    再来看栗子:

    unsigned short a = -1;
    

    a变量的空间里存储着-1的补码(1111 1111 1111 1111),因为short有两个字节,所以有16个比特位。
    这个short定义时说了unsigned short吧?所以此short无符号short.
    那它在进行整型提升时,用规则a。我管你原来是什么数!现在我就知道你是无符号数!
    那我对你进行整型提升时,我只管高位补2个字节的0就行了。
    即(0000 0000 0000 0000 1111 1111 1111 1111
    今天就是天王老子来了,只要你是无符号数!我照样只管高位补0,把你补成4个字节就行。

    注意注意!注意!

    不要觉得charshort在存储时,就发生了整型提升!发生这个整型提升的前提是它们参与整型运算!!而且整型运算结束后,4个字节的数据将发生截断,再返回值。也就是说,运算完成后,CPU返回值的字节数仍为这个数据原本类型的字节数,而不是提升后的字节数。截断的规则是留低位弃高位。

    理解没理解的关键在于你现在知道整型提升的数据在哪存着吗?

    CPU的寄存器!!!!!寄存器!

    你懂了?上道例题考察你一下!

    int main()
    {
    	char a = 0xb6;
    	short b = 0xb600;
    	int c = 0xb6000000;
    	if(a==0xb6)
    		printf("a");
    	if(b==0xb600)
    		printf("b");
    	if(c==0xb6000000)
    		printf("c");
    	return 0;
    }
    

    你猜程序打印结果是啥?

    abc? ab? ac? bc? b? c?
    

    容我问一句!==在哪里进行?它是逻辑运算,在CPU上进行,所以左右两边的数据在哪?对!寄存器register! 所以数据要不要发生整型提升?要的!

    咱们来剖析一下代码

    if(a==0xb6)
    

    ==左边的a是char型,所以a是有符号数,发生整型提升,a为0xffffffb6;
    ==左边的0xb6是字面常量,是有符号数,写完整是0x000000b6
    相等吗?不相等!条件不成立,不打印!

    if(b==0xb600)
    

    ==左边的b是short型,所以b是有符号数,发生整型提升,b为0xffffb600;
    ==左边的0xb6是字面常量,是有符号数,写完整是0x0000b600
    相等吗?不相等!条件不成立,不打印!

    if(c==0xb6000000)
    

    ==左边的c是int型,右边4个字节数,要发生整型提升吗?不要!
    条件成立。
    所以程序运行结果就是 c
    result

    嘿嘿嘿

    懂了?
    来,思考一下,结果是啥

    	char a = 255;
    	unsigned char b = -1;
    
    	printf("a = %u\n", a);
    	printf("b = %u\n", b);
    

    result2
    再送一句话:
    初始化或赋值时只关心该变量提供的空间;
    提取内容时要先看数据的类型。

    第一句话:不管你定义啥类型变量,我只需要等号右边数据的补码放进你的空间就行
    第二句话:当你要用这个变量时,要先看该变量的定义类型,再看需不需要整型提升,需要的话,怎么提升,提升完了再看读取这个数据的类型。
    result3

    更多相关内容
  • 提升度和零事务的关系 先验原则 实际案例 代码实战 频繁项集和支持度 置信度调用 文末资源推荐 每文一语 走进关联规则 什么是关联规则? 情景引入:啤酒与尿布 在一家超市里,有一个有趣的现象:尿布和...

    目录

    🍎走进关联规则

    🍊什么是关联规则?

    🍒关联规则的分类

    🍉关联规则的基本概念

     置信度的局限——错估某个关联规则的重要性

    提升度和零事务的关系

    先验原则

    实际案例

     代码实战

    频繁项集和支持度

    置信度调用

     文末资源推荐

    每文一语


    🍎走进关联规则

    🍊什么是关联规则?

    🐾🐾情景引入:🍺啤酒与尿布🍼

    在一家超市里,有一个有趣的现象:尿布和啤酒赫然摆在一起出售。但是这个奇怪的举措却使尿布和啤酒的销量双双增加了。这不是一个笑话,而是发生在美国沃尔玛连锁店超市的真实案例,并一直为商家所津津乐道。沃尔玛拥有世界上最大的数据仓库系统,为了能够准确了解顾客在其门店的购买习惯,沃尔玛对其顾客的购物行为进行购物篮分析,想知道顾客经常一起购买的商品有哪些。沃尔玛数据仓库里集中了其各门店的详细原始交易数据。在这些原始交易数据的基础上,沃尔玛利用数据挖掘方法对这些数据进行分析和挖掘。一个意外的发现是:"跟尿布一起购买最多的商品竟是啤酒

    经过大量实际调查和分析,揭示了一个隐藏在"尿布与啤酒"背后的美国人的一种行为模式:在美国,一些年轻的父亲下班后经常要到超市去买婴儿尿布,而他们中有30%~40%的人同时也为自己买一些啤酒。产生这一现象的原因是:美国的太太们常叮嘱她们的丈夫下班后为小孩买尿布,而丈夫们在买尿布后又随手带回了他们喜欢的啤酒。

    这就是隐藏在实际生活中的关联规则吗,也是数据挖掘的一种形式,生活中的各类事物都会产生价值,善于挖掘事物的价值就会有不一样的价值。

    联规则最初提出的动机是针对购物篮分析(Market Basket Analysis)问题提出的。假设分店经理想更多的了解顾客的购物习惯。特别是,想知道哪些商品顾客可能会在一次购物时同时购买?

    为回答该问题,可以对商店的顾客事物零售数量进行购物篮分析。该过程通过发现顾客放入“购物篮”中的不同商品之间的关联,分析顾客的购物习惯。这种关联的发现可以帮助零售商了解哪些商品频繁的被顾客同时购买,从而帮助他们开发更好的营销策略。

    关联规则是指事物间的相互联系,反映了一个事物与其他事物之间的相互依存性和关联性。如果两个或者多个事物之间存在一定的关联关系,那么其中一个事物就能够通过其他事物预测得到。

    🍒关联规则的分类

    按处理值分类,关联规则可以分为量化型和布尔型

    布尔型关联规则是研究数据项在某个事务中是否会出现。量化型关联规则主要是离散型的数据,关联规则中的数据项是数量型的。

    在对量化进行关联规则进行挖掘时,通常使用统计学、离散方法等对量化数值进行离散化。分化成几个离散区间,从而转换成布尔型关联规则挖掘。

    关联规则按所涉及的抽象层次可以分为单层和多层

    比如每科成绩之间的关联挖掘就是单层的。而专业课、公共课等之间的关联挖掘,就是多层的。因为 他们是属于不同层级。

    根据数据维数则可以分为单维和多维

    比如,购买网球,只涉及到一个维度。年龄购买网球,则涉及到年龄和网球两个维度。

    🍉关联规则的基本概念

    (1)项

    对一个数据表而言,表的每个字段都具有一个或多个不同的值。字段的每种取值都是一个项Item。

    (2)项集

    项的集合称为项集itemset。包含k个项的项集被称为k-项集,k表示项集中项的数目。由所有的项所构成的集合是最大的项集,一般用符号I表示。

    (3)事务

    事务是项的集合。本质上,一个事务就是事实表中的一条记录。事务是项集I的子集。事务的集合称为事务集。一般用符号D表示事务集/事务数据库。

    (4)关联规则

    给定一个事务集D,挖掘关联规则的问题就变成如何产生支持度和可信度分别大于用户给定的最小支持度和最小可信度的关联规则的问题。(标准)

    (5)支持度(同时,交;元组总数)

    若D中的事务包含A∪B的百分比为s,则称关联规则AB的支持度为s。即:support(AB )= P(A∪B ) = 包含A和B的元组数/元组总数

    (6)可信度(同时,交;条件概率)

    若D中包含A的事务同时也包含B的的百分比为c,则称关联规则 AB 的置信度/可信度为c,即:confidence(AB )=P(B|A) = 包含A和包含B的元组数/包含A的元组数 = support(A∪B )/support(A)

    根据上面的例子,可以求解到苹果——>啤酒的置信度=3/8 /4/8=3/4

    75%的置信度

    (7)频繁项集

    项集的出现频率是包含项集的事务数,简称项集的频率;项集满足最小支持度阈值minsup,如果项集的出现频率大于或等于minsup与D中事务总数的乘积;满足最小支持阈值的项集就称为频繁项集(大项集)。频繁k项集的集合记为Lk;

    如何得出频繁项集,apriori算法的价值所在

    (8)强关联规则

    大于或等于最小支持度阈值和最小置信度阈值的规则叫做强关联规则

    关联分析的最终目的,就是为了找出强关联规则❗️❗️❗️❗️❗️

    算法

    那么,关联规则的本质,其实就是挖掘频繁项,那么算法的目的也就是尽可能快速有效的挖掘不同事物间 关系出现的频率。

    而衡量规则是否成立的两个参考维度,就是支持度和置信度。

    常用的算法有 Apriori 算法 ,FP-growth 算法。这两个算法,前者主要用迭代方法挖掘,不适用于多维挖掘。后者利用存储优化,大幅提高了挖掘性能。

    (9)Lift(提升度)

    指A项和B项一同出现的频率,但同时要考虑这两项各自出现的频率。公式表达:{A→B}的提升度={A→B}的置信度/P(B):

    提升度反映了关联规则中的A与B的相关性,提升度>1且越高表明正相关性越高,提升度<1且越低表明负相关性越高,提升度=1表明没有相关性负值,商品之间具有相互排斥的作用。

    🎈🎈 通过了解上面的一些概念知识,这里给出来一个具体的实例:

    事务: 每一条交易称为一个事务,例如:上表中包含8个事务。
    项:    交易中的每一个物品称为一个项,例如:苹果、啤酒。
    项集:包含零个或者多个项的集合叫做项集,例如{苹果,啤酒} 、{牛奶,啤酒,米饭}。
     k-项集:包含k个项的项集叫做k-项集。例如{苹果}叫做1-项集,{牛奶,啤酒,米饭}叫做3-项集。
    前件和后件:对于规则{苹果}->{啤酒},{苹果}叫前件,{啤酒}叫后件。

    📢 📣🍩🍩下面也通过对三个度量指标进行实例的分析

    1️⃣ 支持度:

    {苹果}在8次交易中出现了4次,所以其支持度为50%。

    一个项集也可以包含多项,比如{苹果,啤酒,米饭}的支持度为2/8,即25%。

    可以人为设定一个支持度阈值,当某个项集的支持度高于这个阈值时,我们就把它称为频繁项集。

    2️⃣ 置信度:

    {苹果→啤酒}的置信度=(支持度{苹果,啤酒}/支持度{苹果})=3/4,即75%。

    置信度有一个缺点,那就是它可能会错估某个关联规则的重要性。只考虑了苹果的购买频率,而并未考虑啤酒的购买频率。如果啤酒也很受欢迎(支持度很高),如上表,那么包含苹果的交易显然很有可能也包含啤酒,这会抬高置信度指标。

    3️⃣ 提升度:

    {苹果→啤酒}的提升度等于{苹果→啤酒}的置信度除以{啤酒}的支持度,{苹果→啤酒}的提升度等于1,这表示苹果和啤酒无关联。

    {X→Y}的提升度大于1,这表示如果顾客购买了商品X,那么可能也会购买商品Y;而提升度小于1则表示如果顾客购买了商品X,那么不太可能再购买商品Y。

    为什么说置信度是有缺点的呢?下面我们看一个实际的例子@快来看📢 📣📢

     置信度的局限——错估某个关联规则的重要性

    📑实际案例

     各商品在与啤酒相关的关联规则中的支持度 

    置信度很高,但是提升度较低,关联效果不好!

    {啤酒→汽水}规则的置信度最高,为17.8%。然而,在所有交易中,二者出现的频率都很高,所以它们之间的关联可能只是巧合。这一点可以通过其提升度为1得到印证,即购买啤酒和购买汽水这两个行为之间并不存在关联

    置信度很低,但是关联效果较好!

    比如{啤酒→男士护肤品}规则的置信度低,这是因为男士护肤品的总购买量不大。

    尽管如此,如果一位顾客买了男士护肤品,那么很有可能也会买啤酒,这一点可以从较高的提升度(2.6)推断出来。

    提升度为负数,无关联!

    {啤酒→浆果}的情况则恰好相反。从提升度小于1这一点,我们可以得出结论:如果一位顾客购买了啤酒,那么可能不会买浆果。

    虽然很容易算出各个商品组合的销售频率,但是商家往往更感兴趣的是所有的热销商品组合。为此,需要先为每种可能的商品组合计算支持度,然后找到支持度高于指定阈值的商品组合。

    那么如何去计算和找出热销商品的组合策略呢?手动的去就是,综合比对吗?如果是在理解算法原理,那倒是可以,但是如果是在进行项目实战,显然无法进行。

    提升度难道是最好的判断标准吗?显然不是,下面我们一起看看,提升度会受到哪些因素的影响吧!以及提升度的来源是什么?

    提升度和零事务的关系

    假设:10000个超市订单(10000个事务),其中购买三元牛奶(A事务)的6000个,购买伊利牛奶(B事务)的7500个,4000个同时包含两者。

    三元牛奶(A事务)和伊利牛奶(B事务)的支持度为:0.4
    三元牛奶(A事务)对伊利牛奶(B事务)的置信度为:0.67

    说明在购买三元牛奶后,有0.67的用户去购买伊利牛奶。

    伊利牛奶(B事务)对三元牛奶(A事务)的置信度为:0.53

    说明在购买伊利牛奶后,有0.53的用户去购买三元牛奶。

    在没有任何条件下,B事务的出现的比例是0.75,而出现A事务,且同时出现B事务的比例是0.67,也就是说设置了A事务出现这个条件,B事务出现的比例反而降低了。这说明A事务和B事务是排斥的。

    我们把0.67/0.75的比值作为提升度,即P(B|A)/P(B),称之为A条件对B事务的提升度,即有A作为前提,对B出现的概率有什么样的影响,如果提升度=1说明A和B没有任何关联,如果<1,说明A事务和B事务是排斥的,>1,我们认为A和B是有关联的,但是在具体的应用之中,我们认为提升度>3才算作值得认可的关联。

    提升度是一种很简单的判断关联关系的手段,但是在实际应用过程中受零事务的影响比较大,零事务在上面例子中可以理解为既没有购买三元牛奶也没有购买伊利牛奶的订单。

    数值为10000-4000-2000-3500=500,可见在本例中,零事务非常小,但是在现实情况中,零事务是很大的。在本例中如果保持其他数据不变,把10000个事务改成1000000个事务,那么计算出的提升度就会明显增大,此时的零事务很大(1000000-4000-2000-3500),可见提升度是与零事务有关的,零事务越多,提升度越高。

    先验原则

    简单地说,先验原则是指,如果某个项集出现得不频繁,那么包含它的任何更大的项集必定也出现得不频繁。这就是说,如果{啤酒}是非频繁项集,那么{啤酒,比萨}也必定是非频繁项集。因此,在整理频繁项集列表时,既不需要考虑{啤酒,比萨},也不需要考虑其他任何包含啤酒的项集。

    随后就会引入最小支持度和最小置信度的概念

    步骤1:列出只包含一个元素的项集,比如{苹果}和{梨}。

    步骤2:计算每个项集的支持度,保留那些满足最小支持度阈值条件的项集,淘汰不满足的项集。

    步骤3:向候选项集(淘汰步骤2不满足的项集后的结果)中增加一个元素,并利用在步骤2中保留下来的项集产生所有可能的组合。

    步骤4:重复步骤2和步骤3,为越来越大的项集确定支持度,直到没有待检查的新项集。
     

    举个例子,假设我们的任务是找到具有高置信度的关联规则。如果{啤酒,薯片→苹果}规则的置信度很低,那么所有包含相同元素并且箭头右侧有苹果的规则都有很低的置信度,包括{啤酒→苹果,薯片}和{薯片→苹果,啤酒}。如前所述,根据先验原则,这些置信度较低的规则会被移除。这样一来,待检查的候选规则就更少了。

    这样对计算的复杂度和效率就会有很大的提升空间

    实际案例

    🍝下面给出一个具体的关联规则的案例🍝

     代码实战

    频繁项集和支持度

    from numpy import *
     
    # 构造数据
    def loadDataSet():
        return [[1, 3, 4], [2, 3, 5], [1, 2, 3, 5], [2, 5]]
     
    # 将所有元素转换为frozenset型字典,存放到列表中
    def createC1(dataSet):
        C1 = []
        for transaction in dataSet:
            for item in transaction:
                if not [item] in C1:
                    C1.append([item])
        C1.sort()
        # 使用frozenset是为了后面可以将这些值作为字典的键
        return list(map(frozenset, C1))  # frozenset一种不可变的集合,set可变集合
     
    # 过滤掉不符合支持度的集合
    # 返回 频繁项集列表retList 所有元素的支持度字典
    def scanD(D, Ck, minSupport):
        ssCnt = {}
        for tid in D:
            for can in Ck:
                if can.issubset(tid):   # 判断can是否是tid的《子集》 (这里使用子集的方式来判断两者的关系)
                    if can not in ssCnt:    # 统计该值在整个记录中满足子集的次数(以字典的形式记录,frozenset为键)
                        ssCnt[can] = 1
                    else:
                        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 # 排除不符合支持度元素后的元素 每个元素支持度
     
    # 生成所有可以组合的集合
    # 频繁项集列表Lk 项集元素个数k  [frozenset({2, 3}), frozenset({3, 5})] -> [frozenset({2, 3, 5})]
    def aprioriGen(Lk, k):
        retList = []
        lenLk = len(Lk)
        for i in range(lenLk): # 两层循环比较Lk中的每个元素与其它元素
            for j in range(i+1, lenLk):
                L1 = list(Lk[i])[:k-2]  # 将集合转为list后取值
                L2 = list(Lk[j])[:k-2]
                L1.sort(); L2.sort()        # 这里说明一下:该函数每次比较两个list的前k-2个元素,如果相同则求并集得到k个元素的集合
                if L1==L2:
                    retList.append(Lk[i] | Lk[j]) # 求并集
        return retList  # 返回频繁项集列表Ck
     
    # 封装所有步骤的函数
    # 返回 所有满足大于阈值的组合 集合支持度列表
    def apriori(dataSet, minSupport = 0.5):
        D = 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})]
        L1, supportData = scanD(D, C1, minSupport)  # 过滤数据
        L = [L1]
        k = 2
        while (len(L[k-2]) > 0):    # 若仍有满足支持度的集合则继续做关联分析
            Ck = aprioriGen(L[k-2], k)  # Ck候选频繁项集
            Lk, supK = scanD(D, Ck, minSupport) # Lk频繁项集
            supportData.update(supK)    # 更新字典(把新出现的集合:支持度加入到supportData中)
            L.append(Lk)
            k += 1  # 每次新组合的元素都只增加了一个,所以k也+1(k表示元素个数)
        return L, supportData
     
    dataSet = loadDataSet()
    L,suppData = apriori(dataSet)
    print(L)
    print(suppData)

    也可以直接调用包:

    from efficient_apriori import apriori
    
    # 挖掘频繁项集和频繁规则
    itemsets, rules = apriori(transactions, min_support=0.5,  min_confidence=1)
    print("频繁项集:", itemsets)
    print("关联规则:", rules)

    置信度调用

    #!/usr/bin/python
    # -*- coding:utf-8 -*-
    from itertools import combinations
    
    
    #读取数据
    def readdata(filename):
        data = []
        with open(filename, 'r') as f:
            while True:
                line = f.readline()
                if not line:
                    break
                data.append([int(_) for _ in line.split()])
        return data
    
    
    def subtract_item_set(pre_discard_itemset, candidate_set):
        '''
        首先去除候选集中不符合非频繁项集的那些元素,
        在当前候选集中去掉上一轮删除的项集,
        比如{2, 3}是非频繁项集,那么就将删除candidate_set中的{2, 3, x}这些项集
    
        Parameters:
        -----------
        pre_discard_itemset: 上一轮删除的项集
    
        candidate_set: 上一次产生的候选集
    
        Returns:
        --------
        返回经过pre_discard_itemset筛选后的项集列表
        '''
        saved_item_set = set()
        discard_item_set = set()
        for item in candidate_set:
            is_discard = False
            for d_item in pre_discard_itemset:
                if d_item.issubset(item):
                    is_discard = True
            if is_discard:
                discard_item_set.add(tuple(item))
            else:
                saved_item_set.add(tuple(item))
        # saved_item_set, discard_item_set
        return [set(i) for i in saved_item_set], [set(i) for i in discard_item_set]
    
    
    def scan_data_set(data_set, candidate_set, min_support):
        '''
        扫描一遍数据集,从候选集中挑出满足支持度的频繁项集,
        同时记录每个项集的支持度(供后面置信度计算)
        '''
        data_set = [set(i) for i in data_set]
        data_set_size = len(data_set)
        candidate_set_size = len(candidate_set)
        cand_set_count = [0 for i in range(candidate_set_size)]
    
        # 对候选集中的元素通过遍历数据集得到他们出现的次数
        for i in range(candidate_set_size):
            for ds in data_set:
                if candidate_set[i].issubset(ds):
                    cand_set_count[i] += 1
    
        saved_item_set = []
        discard_item_set = []
        support_data = []
        # 删除不满足支持度的
        for i in range(candidate_set_size):
            support = cand_set_count[i] * 1.0 / data_set_size
            if support >= min_support:
                saved_item_set.append(candidate_set[i])
                support_data.append(support)
            else:
                discard_item_set.append(candidate_set[i])
        return saved_item_set, discard_item_set, support_data
    
    
    def gen_cand_set(data_set, previous_freq_set, k):
        '''
        从上一次生成的候选集中产生本次的候选集(未经过支持度筛选处理的),
        只是单纯生成下一轮的组合集
    
        Parameters:
        -----------
        data_set: 数据集,用以生成k为1的项集
    
        previous_freq_set: 上一次产生的候选集
    
        k: 本次产生的候选集中项目的大小
    
        Returns:
        --------
        返回列表存储的项集,每个项集是一个集合set, [{0}, {1}, {2}, {3}, {4}...]
        '''
        if k == 1:
            # 列表解析
            item_set = set([item for sublist in data_set for item in sublist])  # 或者item_set = set(sum(data_set, []))
            return [set([i]) for i in item_set]
        elif k > 1:
            cur_freq_set = set()
            pre_fre_set_len = len(previous_freq_set)
            for i in range(pre_fre_set_len):
                for j in range(i + 1, pre_fre_set_len):
                    # 遍历所有的两两组合,并将其加入到集合中
                    # {(1, 2, 3), (1, 3, 5), (2, 3, 4)}
                    s = previous_freq_set[i] | previous_freq_set[j]
                    if len(s) == k:
                        cur_freq_set.add(tuple(s))
        return [set(i) for i in cur_freq_set]
    
    
    def gen_frequecy_set(data_set, min_support):
        '''
        生成频繁项集
    
        Returns:
        --------
        freq_item_set: [[set(item1), set(item2)..]...] 存储频繁项集
        item_set_support: [[support_score1, s_score2..]] 每个项集对应的支持度分值
        '''
        freq_item_set = []
        item_set_support = []
        discard_item_set = None
        cur_dis_item_set_1, cur_dis_item_set_2 = [], []
        cur_item_set_size = 0
        while True:
            # 循环产生项集大小为1, 2...的项集
            cur_item_set_size += 1
            if cur_item_set_size == 1:
                # 产生初始的候选集
                cur_candiate_set = gen_cand_set(data_set, [], cur_item_set_size)
                # 将候选集分成要满足支持度的集合和不满足支持度的集合,同时记录满足支持度集合对应的支持度分值
                saved_item_set, cur_dis_item_set_1, support_data = scan_data_set(data_set, cur_candiate_set, min_support)
            else:
                # 生成该轮候选集
                cur_candiate_set = gen_cand_set(data_set, freq_item_set[-1], cur_item_set_size)
                # 去除候选集中不符合非频繁项集的那些元素
                cur_candiate_set, cur_dis_item_set_1 = subtract_item_set(discard_item_set, cur_candiate_set)
                # 对剩下的候选集,进行遍历数据集,得到保存、丢弃、支持度集合
                saved_item_set, cur_dis_item_set_2, support_data = scan_data_set(data_set, cur_candiate_set, min_support)
            if saved_item_set == []:  # 如果该轮没有产生任何频繁项集,则下一轮也不会产生新的频繁项集了,退出
                break
            freq_item_set.append(saved_item_set)  # freq_item_set存储每一轮产生的频繁项集
    
            discard_item_set = cur_dis_item_set_1  # discard_item_set存储每一轮产生的要丢弃的项集
            discard_item_set.extend(cur_dis_item_set_2)
    
            item_set_support.append(support_data)  # item_set_support存储每一轮产生的频繁项集对应的支持度值
        return freq_item_set, item_set_support
    
    
    def gen_association_rules(freq_item_set, support_data, min_confd):
        '''
        生成关联规则
    
        Returns:
        --------
        association_rules: [(set(item1, item2, ...), itemx, confidence_score), ..]
        存储关联规则,list存储,每个元素都是一个3元组,分别表示item1 和 item2.. 推出 itemx,置信度为confidence_score
        '''
        association_rules = []
        for i in range(1, len(freq_item_set)):
            for freq_item in freq_item_set[i]:  # 对频繁项集的每一项尝试生成关联规则
                gen_rules(freq_item, support_data, min_confd, association_rules)
        return association_rules
    
    
    def gen_rules(freq_item, support_data, min_confd, association_rules):
        '''
        生成关联规则,然后存储到association_rules中
        '''
        if len(freq_item) >= 2:  # 遍历二阶及以上的频繁项集
            for i in range(1, len(freq_item)):  # 生成多种关联规则
                for item in combinations(freq_item, i):  # 遍历长度为1的item的组合
                    conf = support_data[frozenset(freq_item)] / float(support_data[frozenset(freq_item) - frozenset(item)])
                    if conf >= min_confd:
                        association_rules.append((freq_item - set(item), item, conf))
                        gen_rules(freq_item - set(item), support_data, min_confd, association_rules)
    
    
    def support_map(freq_item_set, item_set_support):
        '''
        将生成的频繁项集和每个项集对应的支持度对应起来
    
        Returns:
        --------
        support_data: {frozenset(item1, item2..): support_score, ..}
        '''
        support_data = {}
        for i in range(len(freq_item_set)):
            for j in range(len(freq_item_set[i])):
                support_data[frozenset(freq_item_set[i][j])] = item_set_support[i][j]
        return support_data
    
    
    def apriori_gen_rules(data_set, min_support, min_confd):
        '''
        利用apriori算法生成关联规则分为两步:
        Step1:生成频繁项集
        Step2:生成关联规则
    
        Parameters:
        -----------
        data_set: item list
    
        min_support: 项集需要满足的最小支持度,|X U Y| / |All|
    
        min_confd: 项集之间关系需要满足的最小置信度,|X U Y| / |X|
    
        Returns:
        --------
        rules: 通过apriori算法挖掘出的关联规则
        '''
        freq_item_set, item_set_support = gen_frequecy_set(data_set, min_support)  # 利用Apriori算法生成频繁项集和对应的支持度
        support_data = support_map(freq_item_set, item_set_support)  # 将频繁项集和支持度联系起来
        rules = gen_association_rules(freq_item_set, support_data, min_confd)  # 利用频繁项集、对应的支持度和置信度生成关联规则
        return rules
    
    
    if __name__ == '__main__':
        data_set = readdata("DATA.txt")
        min_support = 0.2 # 最小支持度
        min_confd = 0.4  # 可信度或支持度
        rules = apriori_gen_rules(data_set=data_set, min_support=min_support, min_confd=min_confd)
        print(sorted(rules, key=lambda x: x[2], reverse=True))

     文末资源推荐

    🍓 🍑 🍈 🍌 🍐 🍍 🍠 🍆 🍅 🌽

    点击下方即可下载 ⤵️⤵️⤵️⤵️⤵️

    Python爬取知网论文信息,包含数据爬取、数据分析、数据可视化代码

    每文一语

    爱不释手,才是爱的意义

    展开全文
  • Haar小波提升算法

    千次阅读 2022-04-02 09:56:57
    提升小波又称为第二代小波,最早是由 Sweldens W.博士于 1995 年在贝尔实验室提出,相对于 Mallat 算法而言,提升小波抛弃了原有的傅里叶变换思想,可在时域中完成正交小波的构造,具有算法简单、运算速度快、占用...

    传统的小波变换是在傅里叶变换的基础上演变而来,计算过程中存在着大量的卷积运算或是乘累加的计算,如若在硬件上实现,势必会消耗大量的寄存器资源,而且速度也上不去。提升小波又称为第二代小波,最早是由 Sweldens W.博士于 1995 年在贝尔实验室提出,相对于 Mallat 算法而言,提升小波抛弃了原有的傅里叶变换思想,可在时域中完成正交小波的构造,具有算法简单、运算速度快、占用内存少等优点,而且还能实现整数到整数小波变换,这对于硬件上实现小波变换来说无疑是个天大的好消息。

    小波变换的提升算法主要由分裂(Split)、预测(Prediction)和更新(Update)三个部分构成。分裂是将一个信号分裂成两个信号,预测主要作用是消除第一步分裂之后所留下的数据冗余,更新则是起到一个修正数据的作用。下面将讨论每一步的具体实现过程。

          1)分裂:分裂是将原始信号 X(n) 分裂成两个集合:Xe(n) 和Xo(n) 。最常用的分裂方法是惰性分裂,即对信号 X(n) 进行奇偶采样,其中偶采样构成集合Xe(n) ,奇采样构成集合Xo(n) ,即:

    相反地,可以通过 X e(n) 和 X o(n) 来恢复信号 X(n) 。

    2)预测:由于Xe(n) 和Xo(n) 都是通过对信号 X(n) 进行采样得到的,所以Xe(n) 和Xo(n) 之间必定存在着高度的相关性。因此,可以利用其中一个集合来预测另一个集合。通常习惯就是利用偶子集 Xe(n) 来预测奇子集Xo(n) ,其
    预测误差定义为:

     等式中的 P(Xe(n))为预测算子。通常采用多项式插值作为预测算子,当确定预测算子之后,便可以通过偶子集 Xe(n) 和预测误差 d(n) 来恢复奇子集Xo(n) ,进而可以恢复原始信号 X(n) ,

    由于预测误差 d(n) 表示原始信号 X(n) 局部区域的低频分量误差,故预测误差 d(n) 可看作是信号的高频分量。

    3)更新:低频信号保留了原始信号的绝大部信息,为了使其更逼近原始信号的整体特征(如均值等),确保整体特性和原始信号相同,则需要一个更新过程,来对数据进行修正,其过程如下:

    其中U() 为更新算子。

     提升小波的分解与重构示意图。信号 X(n) 首先分裂成Xe(n) 和 Xo(n) 两个信号,然后用 Xe(n)对Xo(n)进行预测,得到预测误差 d(n) ,最后用预测误差 d(n) 来更新信号 Xe(n) ,从而获得进行信号 c(n) 。重构过程则与之相反

    Haar 小波变换的提升算法:

    本小节将介绍 Haar 小波的提升算法及其原位计算,即在不新增内存的情况下实现小波变换。
      定义x1和x2 两个数,其低频近似系数 c 和高频细节系数 d 分别为:

     则{x1, x2} 的 Haar 小波变换结果为 {c, d}。其逆变换恢复x1 、x2 的公式为:

    若对于长度为 2n的信号,则其变换结果为:

    多级 Haar 小波变换的分解与重构的过程:

    为了实现原位计算,可先计算出细节系数 d ,并将结果 d 存放在原x2 的位置上,接着用x1和 d 的值计算近似系数 c 的值最后将 c 存放在x1 的位置上。内存数据的变化过程。

    同理,可利用逆变换实现原位数据恢复。  

          小波指的是一种能量在时域非常集中的波,它的能量有限,都集中在某一点附近,而且积分的值为零,这说明它与傅里叶波一样是正交波。

          图像的傅里叶变换是将图像信号分解为各种不同频率的正弦波。同样,小波变换是将图像信号分解为由原始小波位移和缩放之后的一组小波。小波在图像处理里被称为图像显微镜,原因在于它的多分辨率分解能力可以将图片信息一层一层分解剥离开来。剥离的手段就是通过低通和高通滤波器。

           小波变换可以和傅里叶变换结合起来理解。傅里叶变换是用一系列不同频率的正余弦函数去分解原函数,变换后得到是原函数在正余弦不同频率下的系数。小波变换使用一系列的不同尺度的小波去分解原函数,变换后得到的是原函数在不同尺度小波下的系数。不同的小波通过平移与尺度变换分解,平移是为了得到原函数的时间特性,尺度变换是为了得到原函数的频率特性。

    小波变换步骤:

    1.把小波w(t)和原函数f(t)的开始部分进行比较,计算系数C。系数C表示该部分函数与小波的相似程度。

    2.把小波向右移k单位,得到小波w(t-k),重复1。重复该步骤直至函数f结束.

    3.扩展小波w(t),得到小波w(t/2),重复步骤1,2.

    4.不断扩展小波,重复1,2,3.

    我这里使用的haar小波,缩放函数是[1 1],小波函数是[1 -1]。是最简单的小波了。

    假设一张图片只有4个像素,其经过2-D DWT之后得到4张子图,每个子图的详细计算过程如下:
    在这里插入图片描述

            图像可以看作是一组二维数据,而 Haar 提升小波变换是一维变换,为了实现图像的二维变换,可通过对行和列分别进行变换来达到二维变换的目的。图像数据进来时,首先进行行变换,变换结果按照树状结果存储到SDRAM 中,图像的一行数据变换结果也存储在同一行,近似系数存放在前,
    细节系数存放在后,如图 4-6 所示。列变换在行变换结束后进行,依次从SDRAM 中读出每一列的数据进行变换,并将同一列的变换结果存储在一列中,近似系数在前,细节系数在后。

     

    Haar 提升小波变换的 FPGA 实现

    图像小波变换主要分为行变换和列变换,而行变换与列变换之间唯一不同是读取数据的方向不一样,其计算过程都是相同的。在处理方式上,对于第一次行变换可直接时时处理,即对于刚输入的数据可直接进行变换。而对于后续的变换则需要先从 SDRAM 中读取数据再做变换处理。
      图 4-7 给出了小波行列变换的过程示意图,图像数据进来直接进行变换,同时将变换结果写入 SDRAM。行变化完成过后紧接着进行列变换处理。在列变换的过程中,需要先从 SDRAM 读取行变换的结果,再进行计算,同时将计算结果存入 SDRAM 中。为了防止数据覆盖,需要把 SDRAM 划分成两个存储模块,一个存储上一次的计算结果,另一个存储当前计算结果。在下一次进行变换时,读取上一次行列变换之后的低频数据进变换,高频数据不动。分别经过三次行列变换之后,就完成了图像的三层小波分解。

    Haar 提升小波变换原理框图如图 4-8 所示,数据进来先做一个缓存,当下一次数据进来时,则同时进行求和、求差运算,之后再将求和之后的结果右移一位,获得变换后的近似系数。为了保证结果的同步性,将求差之后的结果延时一个时钟,这样就可以同时获得变换之后的近似系数和细节系数。

    为了确保后续的编码过程正确,变换之后的数据位仍然表示当前数据绝对值的大小,在数据位前增加一位符号标记位。在计算时,先判断数据符号位,然后再进行计算。这样一来,数据位宽就变成了 9 位,最高位是符号位,表示数据的正负,低八位为数据位,表示数据的大小。图 4-9 给出了细节系数的计算过程,图中 + 和 -分别表示数据x1 、x2 的正负,最高位 0 为正数,1为负数。

     基于小波变换的图像压缩及其 FPGA 实现-游斌相
    https://blog.csdn.net/baidu_27643275/article/details/84826773

    https://blog.csdn.net/qq_30815237/article/details/89704855

    展开全文
  • 提升测试效率都有哪些具体手段?

    千次阅读 2021-11-23 14:32:57
    相信大部分测试人员脑海里首先会跳出来:“自动化测试”或者“敏捷测试”,没错,自动化和敏捷都可以帮助提升研发效率,但是并不是只要做了就都有这个提升作用。 测试效率提升有以下几个不同段位: 1、提升测试...

    在大部分研发项目经理心中,进度通常往往会放在第一位,其次是成本,最后是质量,当然人员队伍也最好要稳定。天下武功,唯快不破:进度 > 成本 > 质量 > 人

    这个说法并不是绝对,当然今天我们并不是讨论他们之间的优先顺序。而是围绕效率提升,测试可以做什么?

    相信大部分测试人员脑海里首先会跳出来:“自动化测试”或者“敏捷测试”,没错,自动化和敏捷都可以帮助提升研发效率,但是并不是只要做了就都有这个提升作用。

    测试效率提升有以下几个不同段位:

    1、提升测试效率

    提升测试的效率,最有效的手段是制定测试策略。对,你没有看错,是测试策略而不是自动化!

    测试策略提升测试效率的逻辑是:减少不必要的测试,重要的问题早发现早解决。

    测试策略的基础是风险评估,首先从失效概率、失效影响这两个维度,区分高、中、低风险的特性,失效概率是发生错误的可能性,评分一般是依据:同类特性的历史表现,设计中需要考虑的要素多寡,需求变更的频繁程度,是否采用新方法等。失效影响是错误发生造成的影响,评分的一般是参考:错误失效对主要业务流程的影响范围,给研发团队以及客户带来的直接经济损失,修复成本,信誉影响等。这两个风险维度的评分虽然有一些参考维度,但主要是依赖经验。

    风险评估完成后,根据每个测试内容的风险评分,确定测试的时间和强度(测试强度通常是用千行代码用例数来衡量)。原则上高风险的内容要尽可能早测试,低风险的内容在计划安排上灵活性可以大一些。高风险的内容要多测试,比如考虑多种测试设计方法同时使用,安排探索式测试等。测试的过程中,需要持续的分析缺陷数据、指标数据,以确定风险是降低还是升高了,如果发现风险升高,甚至已经成为会阻碍产品发布的问题,则必须进行例外报告,调整开发和测试策略。

    提升测试的效率,基于需求的测试也是有效手段之一,基于需求进行测试设计的目的,是减少不必要的参数组合和虚构的应用场景的测试用例。当然,只基于需求进行测试,往往不那么让人放心,因为总会有意外的情况发生,一般还需要再基于经验、基于错误猜测,或者基于在线应用采集的应用场景进行一些补充。对于特别重要的测试内容,可能还需要基于设计进行更高强度的测试。

    那么,为什么不是自动化?大多数时候,我们是将原本手工执行的功能用自动化的方式来执行,这种情况下自动化测试更多的是服务于质量,其目的是发现新特性对老特性产生的,不为人知的影响。如果新特性每次发布,都导致老特性发生意外的变化,进而导致测试不得不在每个版本都全面测试老特性,那么这种自动化就是提升测试效率的。不过,这种情况比较少见,而且,如果真的发生这种情况,一定是产品架构设计出了问题,优化架构比实现自动化测试的优先级要高。

    2、提升开发效率

    测试活动不再局限于测试活本身,测试帮助提升研发效率,最有效的手段是自动化和工具化,这两个手段是实现TDD和缺陷快速定位的关键措施。

    TDD的作用,是用测试用例的形式表述需求或设计目标,从而确保codeing过程中,始终在做正确的事,在向主干中加入各种分支处理逻辑、或者进行各种修改时,不会破坏已经正确的功能,让开发可以放心的修改缺陷或者重构代码。在TDD实施中,测试的主要价值是提供趁手的工具,这个工具不仅要能够驱动测试用例执行,还要让开发很方便的构建测试用例及其执行所需的条件。我们有些团队在TDD实施的早期,把TDD用例编写和调试的工作也交给测试完成,这种方式无法让开发及时验证自己的每一次改动,做不到及时的质量反馈,也起不到TDD宣称的那些作用,不建议采用。

    缺陷快速定位为什么要拿出来讲呢?因为,我们曾经统计过开发的工作量,在实现阶段,大概有1/3~1/2的开发工作量是耗费在缺陷的确认、重现、定位、修改、验证,如果能加快这个过程,则开发效率会有大幅提升。

    通过缺陷辅助定位工具,可以提高这部分工作的效率。在一个用例执行不通过的时候,工具自动采集缺陷定位所需的信息,如:系统产生的日志和其他过程与结果记录,产生变化的数据库记录,此用例执行覆盖到的代码。通过这些信息,可以在无需重现、无需跟踪执行的情况下定位大部分的问题。当然,要实现这个目的,仅仅有工具是不够的,还需要产品做一些日志上的增强,例如在函数的入口和出口记录函数的输入、输出参数。缺陷修改完成后,再用自动化用例进行验证,就能够对开发的缺陷定位产生积极影响。

    很多团队中,开发会把测试提交的缺陷集中在某个时间去修改,也是为了压缩处理缺陷的时间,但是这样会导致质量风险在开发后期集中爆发,是不值得借鉴的方式。

    提升代码质量,除了TDD和缺陷定位,还可以在环境准备、测试结果采集上,使用工具和自动化提升效率。

    3、提升版本发布效率

    测试服务于研发整体而不是某个环节的效率提升

    测试帮助提升版本发布的效率,主要方法是自动化和CI(持续集成)、持续交付。

    自动化是CI的基础,而自动化及CI是持续交付的基础。

    CI对自动化的要求,除了用测试用例进行自动化的产品验证,还包括自动化的编译、打包、部署、环境检查等。

    持续交付在一般CI的基础上,通常还需要做到应用场景的自动化验证(通常是基于UI的自动化测试,用于冒烟测试)、常规性能的自动化验证,不同环境的统一部署,以及按不同的策略发布。一般的组织中,持续交付主要还是用于向专门的测试团队交付产品版本。某些互联网公司能够做到将持续交付用于生产环境,这种场景下,除了上述能力,还需要在产品上线初期进行自动化的异常侦测,看护系统和业务的正常运行,此外,还应该有比较可靠的系统和数据回滚机制。在生产环境中,要使这个过程安全的走下来,验证用例最好能比较完整的覆盖基本功能和新增需求,也需要根据历史问题不断完善看护、侦测规则。

    发布时对基本功能的覆盖,除了传统的人工编写自动化用例的方式,利用在线运行抓取实际场景是更能让测试适配产品更新节奏的方式。

    理想情况下,CI可以做到每天(也可能是每周或者其他的周期)都能够有一个质量过关的版本为上线做好了准备。这是比较理想的情况,我没有见到过真正这样实施的团队,在我们团队中,CI更多的还是在开发过程中,检查程序员的代码质量,起到的是质量门槛的作用。

    持续发布是研发整体的工程能力提升,需要的不仅是研发团队的工具开发能力,还需要在过程管理、配置管理,甚至产品架构、质量文化等方面进行匹配。持续发布的实施,有专门的书籍做了详细介绍。

    4、提升特性交付效率

    测试不是依赖工具和自动化,而是依赖分析设计服务于效率提升

    测试帮助提升特性 交付的效率,需要做到基于需求的测试,此外,敏捷也可以提升特性的交付效率。

    基于需求的测试中,测试帮助研发团队在需求实现方面少一次试错。很多团队认为自己是基于需求进行测试的,但实际上是基于“需求规格说明书”进行测试,后者依赖一份质量优良的文档(标准是,内容完整且正确,研发各个环节都可以完全依据这份文档开展工作,并最终得到正确的特性),但通常这个依赖条件不存在。

    基于需求测试需要做到:

    改善需求质量。利用需求内容模型(5W1H)促进需求内容完整性的提升,利用测试对产品、业务的理解,通过静态测试发现需求中的遗漏、矛盾、错误,从而改善需求,即测试设计输入的质量。

    基于需求测试。根据需求进行单个操作、业务场景和端到端应用场景的测试。并在测试执行时,通过研发测试、邀请客户和需求工程师参与体验和演示等方式,在产品特性半成品上,利用形象的操作过程对抽象的分析进行验证和纠错。

    基于需求的测试除了要会使用上述方法,也比较依赖测试工程师的经验,因为实际应用过程中,我们通常都是参照已经成熟的特性,曾经犯过的错误来进行查缺补漏。

    敏捷提升交付效率的基本逻辑是实现按特性开发和交付。首先,应对这种小步快跑的方式,测试需要及时实现对少量的新增和修改内容进行测试,在最短的时间内进行质量反馈,这要求测试设计、测试执行(自动化测试),甚至发布、部署都要能够在迭代周期的时间窗内完成。其次,按特性发布可以让客户尽可能快的看到和使用特性,以便更快的进行产品应用层面的质量反馈,因此,如果团队按特性开发了,但是并不能按特性 交付,那么对于交付效率的提升还是只完成了一半。

    敏捷是建立在研发的质量文化、产品的架构优化、测试的自动化水平之上的研发模式的演进,如果没有这些基础,仅仅依靠模式的改变是无法既提升效率,又维持质量稳定的。

    围绕效率提升,测试可以开展的工作远不止上面提到的这些,这些都有待我们持续地研究、探索和讨论。。。

    下面是配套资料,对于做【软件测试】的朋友来说应该是最全面最完整的备战仓库,这个仓库也陪伴我走过了最艰难的路程,希望也能帮助到你!å¨è¿éæå¥å¾çæè¿°

    最后: 可以在公众号:程序员小濠 ! 免费领取一份216页软件测试工程师面试宝典文档资料。以及相对应的视频学习教程免费分享!,其中包括了有基础知识、Linux必备、Shell、互联网程序原理、Mysql数据库、抓包工具专题、接口测试工具、测试进阶-Python编程、Web自动化测试、APP自动化测试、接口自动化测试、测试高级持续集成、测试架构开发测试框架、性能测试、安全测试等。

    如果我的博客对你有帮助、如果你喜欢我的博客内容,请 “点赞” “评论” “收藏” 一键三连哦!喜欢软件测试的小伙伴们,可以加入我们的测试技术交流扣扣群:310357728里面有各种软件测试资源和技术讨论)

    展开全文
  • 010108权限提升

    千次阅读 2022-04-03 12:39:37
    提权本质就是提升自己在服务器中的权限,获得更大的权限。 例如:在Windows下普通用户,通过提权获得Administrator一样的权限;在Linux中通过执行编译后的程序,从普通用户权限提升到root账号权限。 2. 提权分类 ...
  • 梯度提升是一种用于回归和分类问题的机器学习技术,其产生的预测模型是弱预测模型的集成,如采用典型的决策树作为弱预测模型,这时则得到了所谓的梯度提升树(GBDT)。GBDT是在传统机器学习算法里面是对真实分布拟合...
  • 提升系统性能的10个建议

    千次阅读 2020-10-25 22:45:45
    如果你的Web应用只跑在一台机器上,那要提升其性能非常简单:换一台更快的,多配几个处理器,多加几条内存,磁盘阵列也要高速的。换了以后,这台机器上跑的WordPress服务器、Node.js或Java应用速度都会加快。(要是...
  • 变量提升2. 函数提升3. 函数优先二、暂时性死区三、总结 通常在直觉上我们会认为代码执行时是从上到下按顺序执行的,但在 JavaScript 中(就同步代码而言),这并不完全正确。 小二,上栗子! 实例 1: a = 2; var ...
  • 函数提升

    千次阅读 2021-03-03 15:21:29
    函数提升 看了一些讲解,对函数提升的解释不是很理解,经过学习,下面总结一下,也是对这个知识点的剖析和巩固。 什么是提升? 引擎会在解释JavaScript代码之前首先对齐进行编译,编译过程中的一部分工作就是找到...
  • Linux 提升权限方法(一) —— sudo

    千次阅读 2022-01-04 19:33:43
    但是程序中有部分代码,却必须要root权限运行,此时,就必须在程序中进行提权操作,暂时将权限提升至root权限。执行完对应代码后,降回原来权限。这样,既能保证程序功能正常,也能保证系统安全。 此文介绍通过sudo...
  • JavaScript之变量提升

    千次阅读 2021-11-20 13:05:57
    1.什么是变量提升(Hoisting)? Javascript中执行上下文 (特别是创建和执行阶段)工作方式的一种认识,在ES6之前是找不到变量提升这个词的 “变量提升”意味着变量和函数的声明会在物理层面移动到代码的最前面,...
  • hackmap-[windows权限提升{windows提权思路}]1.前言1.1.提权分类水平权限提升(越权)垂直权限提升1.2 windows提权概述2.windows基于WebShell提权2.1 前言2.1.1 asp大马 vs aspx大马(windows2003+IIS)1)asp大马2)...
  • 机器学习——提升

    千次阅读 2022-03-31 15:57:31
    提升树(BT,Boosting Tree)是以分类树和回归树为基本分类器的提升方法。提升树被认为是统计学习中性能最好的方法之一。 以决策树为基函数的提升方法称为提升树。 二、提升树模型 提升方法采用加法模型(即基函数...
  • JS变量提升和函数提升的顺序

    千次阅读 多人点赞 2020-10-19 23:25:36
    今天笔试时碰到考察变量提升与函数提升顺序的一道题目,之前只知道var定义的变量会有变量提升以及函数声明也会提升,但没有深入研究他们的顺序以及详细过程。事后查阅资料加上自己的验证,得出了自己对于它们顺序的...
  • 本系列的第一篇选择了一个很值得讨论的问题——变量提升,我们会从遇到问题、分析问题、解决问题、例题测试的方式加深大家对变量提升的认知,一起加油!
  • 机器学习——梯度提升决策树(GBDT)
  • GBDT梯度提升决策树与GBRT梯度提升回归树原理详解 1提升树的原理 2 提升树算法 3GBDT与GBRT 4 GBRT的数学实例 5 API详解 补充集成学习的多样性增强 总结:集成学习中各个算法分别如何做分类和回归的 学GBDT,GBRT之前...
  • 提升度,提升表和提升图 lift chart

    千次阅读 2019-10-31 16:56:40
    提升指数、提升表和提升图(草稿) 胡江堂,北京大学软件与微电子学院 2006-11-5 1. 什么是Lift? I) Lift(提升指数)是评估一个预测模型是否有效的一个度量;这个比值由运用和不运用这个模型所得来的结果计算...
  • 什么是变量提升

    千次阅读 2022-02-16 13:47:39
    变量提升这个问题,通常发生在var声明的变量里,就是说当使用var声明一个变量的时候,该变量会被提升到作用域的顶端,但是赋值的部分并不会被提升。如: console.log(a) var a = 'bar' 在声明a的语句之前,就...
  • Boosting 是一种松散的策略,它将多个简单模型组合成一个复合模型。这个想法的理论来自于随着我们引入更多的简单模型,整个模型会变得越来越强大。...梯度提升通过将一个个回归树进行整合可以使模型预测变得更好
  • 有时候,我们在普通的cmd模式下执行命令,会提示权限不够,需要用管理员权限打开,然后关闭当前... 以上就是cmd怎么用命令直接提升到管理员权限|cmd原有权限提升方法文章,要想了解更多Windows资讯,请继续关注pe吧。
  • 摘要:介绍了提升机的不同保护措施,分析了电动机保护器对提升机设备的保护范围。针对提升机类的设备提出定值优化和增加DCS系统辅助保护的措施,并对可靠性进行了验证,可以做到更加准确地保护负载设备。
  • js中的变量提升和函数提升

    万次阅读 多人点赞 2018-10-30 13:30:09
    有了上面变量提升的说明,函数提升理解起来就比较容易了,但较之变量提升,函数的提升还是有区别的。举例说明: console.log(foo1); // [Function: foo1] foo1(); // foo1 console.log(foo2); // undefined foo...
  • 开发者涨薪指南:提升软、硬实力

    万次阅读 多人点赞 2022-05-11 10:29:13
    阿里巴巴CTO程立(鲁肃)、技术创业者和投资人戴志康、游戏开发者云风提到了技术能力与管理能力的提升,希望能给渴望提升实力的开发者带来启发。 1、硬实力提升 初级开发者:训练逻辑,打好基础 作为与数据打交道的...
  • 梯度提升决策树(Gradient Boosting Decision Tree,GBDT)

    万次阅读 多人点赞 2019-07-07 15:09:56
    梯度提升决策树(Gradient Boosting Decision Tree,GBDT) 集成学习的系列博客: 集成学习(ensemble learning)基础知识 随机森林(random forest) AdaBoost算法(一)——基础知识篇 AdaBoost算法(二)——...
  • sudo命令普通用户提升root权限配置

    千次阅读 2022-03-21 13:55:29
    sudo命令普通用户提升root权限配置 1.概述 在操作linux时候,有些命令需要使用root权限才能执行,如果我们使用的是普通用户可以使用sudo命令将普通用户权限提升到root权限解决权限限制。 使用sudo提升权限也是需要...
  • 信息技术应用能力提升培训心得体会两篇篇一:本月,我进行了“教师信息技术应用能力提升工程”的学习,学习过程中的每一天我都过得非常充实。这次的培训我学习到了很多,每一个视频的内容都非常有意义、有价值。所以...
  • qt中提升控件的操作

    千次阅读 2021-05-19 09:42:26
    我的代码里面自己写了一个类myview,继承自QGraphicsView,然后就把拖到界面上的QGraphicsView控件通过提升控件的方式替换成自己的myview类。 先在工具栏拖一个QGraphicsView到主界面上,如下图: 右击界面上的...
  • 算法能力提升攻略

    千次阅读 2020-12-16 11:37:11
    二、全面提升算法思维三、利用算法产出优秀的作品总结 前言 一、先快速刷完100道题 ???? LeetCode 热题 HOT 100 快速刷完这100道题,不追求每个题的每个解法都能吃透,只是说先克服对于算法的恐惧,第二是对各种类型...
  • 详解函数和变量的声明提升

    千次阅读 多人点赞 2019-11-30 21:46:37
    详细解读—函数和变量的声明提升 一 - 声明提升常见面试题 ☛我们先以几道面试题开头来引入, ☛大家可以先给自己做出一个答案,然后再看文章的思路捋一捋哟。 来一道基础的吧~ var a="Hello"; function test(){ ...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 2,185,167
精华内容 874,066
关键字:

提升

友情链接: 20304284.rar