当前位置: 首页 > web >正文

机器学习实验报告4-Logistic 回归算法

4.1 Logistic回归算法简介

Logistic回归,也称为logistic回归分析,是一种广义的线性回归分析模型。它常用于数据挖掘,疾病自动诊断,经济预测等领域。Logistic回归是一种用于解决二分类问题的机器学习方法,可以估计某种事物的可能性。它是一种线性分类器,针对的是线性可分问题。该模型根据给定的自变量数据集来估计事件的发生概率,由于结果是一个概率,因此因变量的范围在 0 和 1 之间

Logistic回归的名称来源于其使用的逻辑函数,该函数将连续的输入映射到位于0和1之间的输出。这个逻辑函数在处理二分类问题时特别有用,因此被命名为logistic回归。至于logistic回归的起源,它是由统计学家在20世纪初提出的,用于解决二项分布的问题。然而,它在实际应用中被广泛使用是在二战以后,特别是在机器学习和数据挖掘领域。

4.2 算法的基本原理

Logistic回归(逻辑回归)是一种统计方法,主要用于预测二分类(多分类不常用,不做介绍,下同)结果,称为因变量,可以是某疾病是否复发、是否死亡、是否再入院等。逻辑回归的基本思想是使用逻辑函数(通常是Sigmoid函数)将线性回归模型的输出转换成概率。这种转换使得逻辑回归模型能够处理分类问题,尤其是二分类问题。

通俗来讲就是根据数据集进行分类,分类的依据标准是概率。找到一个概率阈值,例如50%:样本属于A类的概率大于50%则为A类,反之为B类。但实际上,不是所有的数据我们都可以一股脑的将他们填充进模型内部进行训练,在统计学中,是有前置条件:这些特征需要相互独立。

  1. Sigmoid函数

在线性回归模型中,输出一般是连续的,对于每一个输入x,都有一个对应的输出y。该模型的定义域和值域都是无穷的。但是对于分类问题,输入可以是连续的[-∞, +∞],但输出则是离散的,通常只有两个值0和1。那么如何将输出限制在[0,1]这个区间呢?这需要我们找到一个函数∅(x),这个函数必须满足定义域为[-∞,+∞],而值域为[0,1]。这样就可以将大于0.5的输出判断为属于1类,小于0.5的输出判断为0类,这就完成了分类问题的预测。我们选择了Sigmoid函数,该函数能够将线性回归问题扩展到非线性回归问题——逻辑回归(Logistic回归)。

首先,我们处理二分类问题。由于分成两类,我们便让其中一类标签为0,另一类为1。Sigmoid函数对于输入的每一组数据,都能映射成0~1之间的数。并且如果函数值大于0.5,就判定属于1,否则属于0。而且函数中需要待定参数,通过利用样本训练,使得这个参数能够对训练集中的数据有很准确的预测。这个函数就是sigmoid函数,该函数可通过公式(1)计算求得。

图1给出了Sigmoid函数在不同坐标尺度下的两条曲线图。当x为0时,Sigmoid函数值为0.5。随着x的增大,对应的Sigmoid值将逼近于1;而随着x的减小,Sigmoid值将逼近于0。如果横坐标刻度足够大,Sigmoid函数看起来很像一个阶跃函数。

图1 Sigmoid函数图

  1. 梯度上升法

我们介绍的第一个最优化算法叫做梯度上升法。梯度上升法基于的思想是:要找到某函数的最大值,最好的方法是沿着该函数的梯度方向探寻。如果梯度记为▽,则函数(x,y)的梯度由下式(2)表示。

这是机器学习中最易造成混淆的一个地方,但在数学上并不难,需要做的只是牢记这些符号的意义。这个梯度意味着要沿x的方向移动

,沿y的方向移动

。其中,函数f(x,y)必须要在待计算的点上有定义并且可微。梯度上升算法沿梯度方向移动了一步,梯度算子总是指向函数值增长最快的方向。这里所说的是移动方向,而未提到移动量的大小。该量值称为步长,记做α。用向量来表示的话,梯度上升算法的选代公式可由公式(3)表示。该公式将一直被迭代执行,直至达到某个停止条件为止,比如迭代次数达到某个指定值或算法达到某个可以允许的误差范围。

4.3 算法实例

以疝气病症马的死亡率为列,基于Logistic回归算法实现分类。这里的数据包含368个样本和28个特征。从一些文献中了解到,疝病是描述马胃肠痛的术语。然而,这种病不一定源自马的胃肠问题,其他问题也可能引发马疝病。该数据集中包含了医院检测马疝病的一些指标,有的指标比较主观,有的指标难以测量,例如马的疼痛级别。

实例操作可分为五个过程。1.收集数据:给定数据文件。2.准备数据:用Python解析文本文件并填充缺失值。3.分析数据:可视化并观察数据。4.训练算法:使用优化算法,找到最佳的系数。5.测试算法:为了量化回归的效果,需要观察错误率。根据错误率决定是否回退到训练阶段,通过改变迭代的次数和步长等参数来得到更好的回归系数。

  1. 收集数据

数据文件以txt格式存储,包含368行样本记录,每行对应一匹马的检测数据。文件首行为特征名称,包括27个客观指标(如白细胞计数、体温、心率等)和1个主观指标(疼痛级别,取值范围为1-10的整数)。部分记录存在缺失值,例如疼痛级别字段中约有15%的数据为空,其他客观指标的缺失率低于5%。数据集最后一列为二分类标签(0表示存活,1表示死亡)。

  1. 准备数据

loadDataSet的函数,其主要功能是从testSet.txt文件中读取数据,并将数据处理成特征矩阵dataMat和标签向量labelMat后返回。loadDataSet函数会打开指定的testSet.txt文件,逐行读取文件内容,对每行数据进行处理,提取出特征和标签信息,然后将特征存储在dataMat列表中,标签存储在labelMat列表中,最后返回这两个列表。

相关代码如下:

def loadDataSet():

    dataMat = []; labelMat = []

    fr = open('testSet.txt')

    for line in fr.readlines():

        lineArr = line.strip().split()

        dataMat.append([1.0, float(lineArr[0]), float(lineArr[1])])

        labelMat.append(int(lineArr[2]))

    return dataMat,labelMat

图2 准备数据

  1. 分析数据

plotBestFit函数,其主要功能是根据给定的权重向量weights对数据集进行可视化展示,同时绘制出逻辑回归模型的决策边界。plotBestFit函数接收一个权重向量weights作为输入,该权重向量通常是通过逻辑回归的梯度上升等优化算法得到的。函数会加载数据集,将数据集中不同类别的样本分别用不同颜色和标记绘制在散点图上,并且根据权重向量绘制出逻辑回归模型的决策边界,最后显示绘制好的图形。

相关代码如下:

def plotBestFit(weights):

    import matplotlib.pyplot as plt

    dataMat,labelMat=loadDataSet()

    dataArr = array(dataMat)

    n = shape(dataArr)[0]

    xcord1 = []; ycord1 = []

    xcord2 = []; ycord2 = []

    for i in range(n):

        if int(labelMat[i])== 1:

            xcord1.append(dataArr[i,1]); ycord1.append(dataArr[i,2])

        else:

            xcord2.append(dataArr[i,1]); ycord2.append(dataArr[i,2])

    fig = plt.figure()

    ax = fig.add_subplot(111)

    ax.scatter(xcord1, ycord1, s=30, c='red', marker='s')

    ax.scatter(xcord2, ycord2, s=30, c='green')

    x = arange(-3.0, 3.0, 0.1)

    y = (-weights[0]-weights[1]*x)/weights[2]

    ax.plot(x, y)

    plt.xlabel('X1'); plt.ylabel('X2');

    plt.show()

图3 分析数据

图4 决策边界

  1. 训练算法

gradAscent的函数,它实现了梯度上升算法,用于求解逻辑回归模型中的最优权重参数。gradAscent函数接收两个参数:dataMatIn是输入的特征矩阵,classLabels是对应的类别标签向量。函数的目标是通过梯度上升算法,找到使得逻辑回归模型似然函数最大化的权重向量。

相关代码如下:

def gradAscent(dataMatIn, classLabels):

    dataMatrix = matrix(dataMatIn)             #convert to NumPy matrix

    labelMat = matrix(classLabels).transpose() #convert to NumPy matrix

    m,n = shape(dataMatrix)

    alpha = 0.001

    maxCycles = 500

    weights = ones((n,1))

    for k in range(maxCycles):              #heavy on matrix operations

        h = sigmoid(dataMatrix*weights)     #matrix mult

        error = (labelMat - h)              #vector subtraction

        weights = weights + alpha * dataMatrix.transpose()* error #matrix mult

    return weights

图5 训练算法

  1. 测试算法

multiTest函数,其功能是多次调用colicTest函数,并计算这些调用结果的平均错误率。colicTest函数会返回一个 0 到 1 之间的随机数当作错误率,而multiTest函数会多次调用colicTest函数,然后计算并输出平均错误率。

相关代码如下:

def multiTest():

    numTests = 10; errorSum=0.0

    for k in range(numTests):

        errorSum += colicTest()

print ("after %d iterations the average error rate is: %f" % (numTests, errorSum/float(numTests)))

def colicTest():

    frTrain = open('horseColicTraining.txt'); frTest = open('horseColicTest.txt')

    trainingSet = []; trainingLabels = []

    for line in frTrain.readlines():

        currLine = line.strip().split('\t')

        lineArr =[]

        for i in range(21):

            lineArr.append(float(currLine[i]))

        trainingSet.append(lineArr)

        trainingLabels.append(float(currLine[21]))

    trainWeights = stocGradAscent1(array(trainingSet), trainingLabels, 1000)

    errorCount = 0; numTestVec = 0.0

    for line in frTest.readlines():

        numTestVec += 1.0

        currLine = line.strip().split('\t')

        lineArr =[]

        for i in range(21):

            lineArr.append(float(currLine[i]))

        if int(classifyVector(array(lineArr), trainWeights))!= int(currLine[21]):

            errorCount += 1

    errorRate = (float(errorCount)/numTestVec)

    print ("the error rate of this test is: %f" % errorRate)

    return errorRate

图6 测试算法

4.4 六悔铭

六悔铭

北宋名相寇准

官行私曲,失时悔;富不俭用,贫时悔;艺不少学,过时悔;见事不学,用时悔;醉发狂言,醒时悔;安不将息,病时悔

它告诉我们,人生在世,应当珍惜时间,及时行乐,但也不要忘记自律和自省。无论是为官、为富,还是为人,都应当以诚信、节俭、学习、自律为准则,这样才能避免在人生的道路上留下遗憾。‍‍‍‍‍‍‍‍‍有些事,错过了,就是一辈子。人生没有回头路,每一步都算数,每一步都该慎重考虑。谁也不想等到老了,坐在摇椅上,满脑子都是“如果当初”。

http://www.xdnf.cn/news/14438.html

相关文章:

  • 如何设计一个既提供绘图Tools又提供example_data的MCP服务器:
  • vulnerable_docker_containement(hard难度)MSF内网穿透、docker逃逸、wpscan爆破。
  • vscode python debugger 如何调试老版本python
  • 论文略读:Personality Alignment of Large Language Models
  • Git里面Stash Changes和UnStash Changes使用
  • LiteRT-LM边缘平台上高效运行语言模型
  • 【Android】 BindService源码流程
  • 如何在Windows上使用qemu安装ubuntu24.04服务器?
  • 408第一季 - 数据结构 - B树与B+树
  • 数据结构---B树
  • 卷积神经网络中的通道注意力机制
  • [游戏实时地图] 地图数据 | 兴趣点数据 | 虚幻引擎SDK接口
  • 软考 系统架构设计师系列知识点之杂项集萃(89)
  • UFS Layout Guide (UFS 2.x)
  • 第11章:Neo4j实际应用案例
  • 把Cmakelist.txt转化为Qt Pro文件的方法
  • 如何让 AI 接入自己的 API?我开发了一个将 OpenAPI 文档转为 MCP 服务的工具
  • 深入理解Kafka Consumer:从理论到实战
  • 简化您的工作流程:在 Azure 中构建高效的逻辑应用程序
  • 电池预测 | 第32讲 Matlab基于CNN-BiLSTM-Attention的锂电池剩余寿命预测,附锂电池最新文章汇集
  • Zustand:小而美的React状态管理库详解
  • React 实现卡牌翻牌游戏
  • AI医生24小时在线:你的健康新‘算法监护人
  • 项目 : 基于正倒排的boost搜索引擎
  • 基于n8n快速开发股票舆情监控对话系统
  • Servlet完整笔记
  • 通过 BLE 和 Wi-Fi 交换优化基于 ID 的远程无人机通信的延迟
  • Bootstrap 5学习教程,从入门到精通, Bootstrap 5 列表组(List Group)语法知识点及案例(14)
  • 【图像处理入门】8. 数学基础与优化:线性代数、概率与算法调优实战
  • Python----OpenCV(图像的绘制——绘制椭圆,绘制文本,添加文字水印,添加图片水印)