Loading [MathJax]/jax/output/CommonHTML/config.js
前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >手撸机器学习算法 - 逻辑回归

手撸机器学习算法 - 逻辑回归

作者头像
HoLoong
发布于 2021-07-01 07:50:43
发布于 2021-07-01 07:50:43
52900
代码可运行
举报
文章被收录于专栏:尼莫的AI小站尼莫的AI小站
运行总次数:0
代码可运行

系列文章目录:

算法介绍

今天我们一起来学习使用非常广泛的分类算法:逻辑回归,是的,你没有看错,虽然它名字里有回归,但是它确实是个分类算法,作为除了感知机以外,最最最简单的分类算法,下面我们把它与感知机对比来进行学习;

从决策边界上看

  • 感知机:决策边界就是类别的分界线,处于错误一侧的点即为分类错误点;
  • 逻辑回归:决策边界表示分为正类和负类均为50%,数据点被分为正类的概率直观上由其到决策边界的距离决定;

以上,对于数据中的噪声,假设噪声点实际为负类,但是被分到正类一侧,如果是感知机,则无法判断,而逻辑回归以概率为基础,如果该噪声点实际被分为正类的概率仅为52%,那么实际上它属于负类的可能性也很大,即逻辑回归认为数据的产生是有一定随机性的,相比于简单的0或1,概率值更能表现其实际情况;

输出函数

从决策边界可知,感知机的输出∈{+1,-1},而逻辑回归的输出为0~1的概率值:

  • 感知机使用sign作为输出函数:sign(wx+b)
  • 逻辑回归使用sigmoid作为概率输出函数:sigmoid(wx+b),sigmoid=1/(1+e^-z),这里z=wx+b,可以看到当z=0时,也就是处于决策边界时,此时sigmoid= 0.5,也就是50%,除此之外,z越大,sigmoid输出越大,可以认为越有可能是正类,反之即为负类,且可以通过极限推导sigmoid区间为(0,1);

如何看待逻辑回归选择Sigmoid作为概率输出函数呢,可以从以下几个点来理解:

  • sigmoid自身性质
    1. 输入是整个实数域,输出是(0,1),输出不包含0和1,使得对于机器学习仅使用整体的一部分作为样本进行训练的场景,很适合处理未出现在样本集中的类别;
    2. 图像曲线对于两侧极值不敏感,二分类的输出符合伯努利分布,输入一般认为符合正态分布,图像曲线也符合这一点;
    3. 易于求导,sigmoid函数的导数为S(wx+b)*(1-S(wx+b)),参数优化过程基本就是求导过程,因此易于求导很重要;
  • 贝叶斯概率推导
    1. sigmoid函数可以由伯努利、正态分布+贝叶斯全概率公式推导得到;

损失函数

  • 感知机:
yi*sign(w*xi+b)

,yi∈{-1,+1},模型分类正确返回值为+1,错误返回值为-1,对所有样本进行求和即可得到score值;

  • 逻辑回归:
ln(1+e^{-(yi*wxi)})

,yi∈{-1,+1},模型分类正确返回值>=0,错误返回值<0,负数绝对值越大,表示错误越严重,对所有样本计算该误差加起来求平均即为逻辑回归的误差函数;

算法推导

从概率角度看Sigmoid

Sigmoid给出了条件概率:

  • 正类的分布:
P(Y=1|X) = Sigmoid(wx+b) = \frac{1}{1+e^{-(wx+b)}}

,其中x~P(X),y~P(Y);

  • 负类的分布:
P(Y=-1|X) = 1-Sigmoid(wx+b) = 1-\frac{1}{1+e^{-(wx+b)}}

函数优化求导

代码实现

初始化相关参数

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
def __init__(self,X,y,epochs=5000,eta=0.1,epsilon=0.001):
    super(LogisticRegression,self).__init__(X,y)
    self.epochs = epochs
    self.eta = eta
    self.epsilon = epsilon
    self.wk = np.array([0 for i in range(self.X.shape[1])])

Sigmoid

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
def sigmoid(self,x):
    return 1/(1+np.exp(-x))

经验损失函数梯度

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
def drhd(self,w):
    '''
    经验误差函数的梯度
    '''
    ew = []
    for i in range(self.X.shape[1]):
        ewi = np.mean(-self.y*self.X[:, i]*np.exp(-self.y*(self.X@w))/(1+np.exp(-self.y*(self.X@w))))
        ew.append(ewi)
    return np.array(ew)

迭代训练

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
def train(self):
    i_,norm = None,None
    for i in range(self.epochs):
        drhdwk = self.drhd(self.wk)
        i_,norm = i,np.linalg.norm(drhdwk)
        if np.linalg.norm(drhdwk) < self.epsilon:
            break
        self.wk = self.wk-self.eta*drhdwk
    return i_,norm,self.wk

运行结果

先看下感知机-口袋算法处理非线性分类问题:

再来对比看下逻辑回归的分类情况:

直觉上看,二者虽然都有一个点分类错误(这是肯定的,因为数据不是线性可分的),但是对于分类错误的×来说,逻辑回归中错误的×距离分割平面更近,也就是说模型对于这个点的判断是比较模糊而不是很肯定的,可以认为是错的不严重,这一点也会反应在损失函数中;

全部代码

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
import numpy as np
from 线性回归最小二乘法矩阵实现 import LinearRegression as LR
from sklearn.datasets import load_iris
import matplotlib.pyplot as plt

class LogisticRegression(LR):
    def __init__(self,X,y,epochs=5000,eta=0.1,epsilon=0.001):
        super(LogisticRegression,self).__init__(X,y)
        self.epochs = epochs
        self.eta = eta
        self.epsilon = epsilon
        self.wk = np.array([0 for i in range(self.X.shape[1])])

    def sigmoid(self,x):
        return 1/(1+np.exp(-x))

    def h(self,x):
        '''
        假设函数
        '''
        return self.sigmoid(x@self.wk.T)

    def drhd(self,w):
        '''
        经验误差函数的梯度
        '''
        ew = []
        for i in range(self.X.shape[1]):
            ewi = np.mean(-self.y*self.X[:, i]*np.exp(-self.y*(self.X@w))/(1+np.exp(-self.y*(self.X@w))))
            ew.append(ewi)
        return np.array(ew)

    def train(self):
        i_,norm = None,None
        for i in range(self.epochs):
            drhdwk = self.drhd(self.wk)
            i_,norm = i,np.linalg.norm(drhdwk)
            if np.linalg.norm(drhdwk) < self.epsilon:
                break
            self.wk = self.wk-self.eta*drhdwk
        return i_,norm,self.wk

    def sign(self,value):
        return 1 if value>=0 else -1

    def predict(self,x):
        return self.sign(self.wk.dot(np.append([1],x)))

if __name__ == '__main__':
    X = np.array([[5,2], [3,2], [2,7], [1,4], [6,1], [4,5], [2,4.5]])
    y = np.array([-1, -1, 1, 1, -1, 1, -1, ])
    # X = np.array([[5,2], [3,2], [2,7], [1,4], [6,1], [4,5]])
    # y = np.array([-1, -1, 1, 1, -1, 1, ])
    iris = load_iris()
    X = iris.data[iris.target<2,:2]
    y = iris.target[iris.target<2]
    y[y==0] = -1

    model = LogisticRegression(X=X,y=y,epochs=10000,eta=.2,epsilon=0.0001)
    i,norm,w = model.train()
    print(f"epochs={i} -> w={w} -> norm={norm:>.8f}")
    for xi,yi in zip(X,y):
        print(yi,model.predict(xi))

    w,b = w[1:],w[0]
    positive = [x for x,y in zip(X,y) if y==1]
    negative = [x for x,y in zip(X,y) if y==-1]
    line = [(-w[0]*x-b)/w[1] for x in [-100,100]]
    plt.title('w='+str(w)+', b='+str(b))
    plt.scatter([x[0] for x in positive],[x[1] for x in positive],c='green',marker='o')
    plt.scatter([x[0] for x in negative],[x[1] for x in negative],c='red',marker='x')
    plt.plot([-100,100],line,c='black')
    plt.xlim(min([x[0] for x in X])-1,max([x[0] for x in X])+1)
    plt.ylim(min([x[1] for x in X])-1,max([x[1] for x in X])+1)
    plt.show()

    iris = load_iris()
    X = iris.data
    y = iris.target
    model = LogisticRegression(X=X,y=y,epochs=1000000,eta=.1,epsilon=0.0005)
    i,norm,w = model.train()
    print(f"epochs={i} -> w={w} -> norm={norm:>.8f}")

最后

逻辑回归几乎是机器学习中应用最为广泛的一种分类算法,由于其简单的思想、良好的数学理论、超强的可解释性,使得在推荐领域、金融领域等发挥了巨大的作用;

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2021-06-24 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
手撸机器学习算法 - 线性回归
如果说感知机是最最最简单的分类算法,那么线性回归就是最最最简单的回归算法,所以这一篇我们就一起来快活的用两种姿势手撸线性回归吧;
HoLoong
2021/06/17
1.2K0
手撸机器学习算法 - 线性回归
手撸机器学习算法 - 非线性问题
前面两篇分别介绍了分类与回归问题中各自最简单的算法,有一点相同的是它们都是线性的,而实际工作中遇到的基本都是非线性问题,而能够处理非线性问题是机器学习有实用价值的基础; 首先,非线性问题在分类与回归中的表现是不同的,在回归问题中,通常指的是无法通过线性模型很好的拟合,而在分类问题中,非线性问题指的是无法通过超平面进行正确的分类;
HoLoong
2021/06/21
7000
手撸机器学习算法 - 非线性问题
手撸机器学习算法 - 感知机
感知机(Perceptron)是最最最简单的机器学习算法(分类),同时也是深度学习中神经元的基础组件;
HoLoong
2021/06/17
6220
手撸机器学习算法 - 感知机
手撸机器学习算法 - 岭回归
今天我们来一起学习一个除了线性回归、多项式回归外最最最简单的回归算法:岭回归,如果用等式来介绍岭回归,那么就是:
HoLoong
2021/06/21
1.1K0
手撸机器学习算法 - 岭回归
机器学习算法(一): 基于逻辑回归的分类预测
逻辑回归(Logistic regression,简称LR)虽然其中带有"回归"两个字,但逻辑回归其实是一个分类模型,并且广泛应用于各个领域之中。虽然现在深度学习相对于这些传统方法更为火热,但实则这些传统方法由于其独特的优势依然广泛应用于各个领域中。
小言从不摸鱼
2024/09/10
1370
机器学习算法整理(三)逻辑回归
逻辑回归是解决分类问题的,那回归问题怎么解决分类问题呢?将样本的特征和样本发生的概率联系起来,概率是一个数。
算法之名
2021/09/14
3600
机器学习算法整理(三)逻辑回归
无比强大的机器学习扩展包MLxtend
mlxtend(machine learning extensions,机器学习扩展)是一个用于日常数据分析、机器学习建模的有用Python库。
皮大大
2024/06/06
2260
【机器学习基础】数学推导+纯Python实现机器学习算法6:感知机
今天笔者要实现的机器学习算法是感知机(perceptron)。感知机是一种较为简单的二分类模型,但由简至繁,感知机却是神经网络和支持向量机的基础。感知机旨在学习能够将输入数据划分为+1/-1的线性分离超平面,所以说整体而言感知机是一种线性模型。因为是线性模型,所以感知机的原理并不复杂,本节笔者就和大家来看一下感知机的基本原理和Python实现。
黄博的机器学习圈子
2020/06/21
7950
机器学习-对数几率回归(逻辑回归)算法
对数几率回归(Logistic Regression),也称逻辑回归,虽然名字中含有回归,但其实是一种分类算法。找一个单调可微函数将分类任务中的真实标记与线性回归模型的预测值联系起来,是一种广义线性回归。
唔仄lo咚锵
2023/05/23
9410
机器学习-对数几率回归(逻辑回归)算法
【机器学习-监督学习】神经网络与多层感知机
  本文将会介绍机器学习中最重要的内容之一——神经网络(neural network,NN),它是深度学习的基础。神经网络的名称来源于生物中的神经元。自有计算机以来,人们就希望能让计算机具有和人类一样的智能,因此,许多研究者将目光放到了人类的大脑结构上。作为生物神经系统的基本单元,神经元在形成智能的过程中起到了关键作用。神经元的结构并不复杂,简单来说,神经元由树突、轴突和细胞体构成。图1是神经元的结构示意图。由其他神经元传来的神经脉冲在细胞间通过神经递质传输。神经递质被树突接收后,相应的神经信号传给细胞体,由细胞体进行处理并积累。当积累神经递质的兴奋性超过了某个阈值,就会触发一个动作电位,将新的信号传至轴突末梢的突触,释放神经递质给下一个神经元。生物的智能、运动等几乎所有生命活动的控制信号都由这些看似简单的神经元进行传输。
Francek Chen
2025/01/22
3460
【机器学习-监督学习】神经网络与多层感知机
机器学习:基于逻辑回归的分类预测
尽管名为“回归”,逻辑回归实际上是一种分类模型,广泛应用于各个领域。当今社会,深度学习在许多方面已取得了显著成果,使得传统方法相形见绌。然而,正是由于这些传统方法所具有的独特优势,它们依然在各个领域发挥着重要作用。
用户3578099
2023/09/01
4690
机器学习:基于逻辑回归的分类预测
Python快速实战机器学习(4) 逻辑回归
机器学习是如今人工智能时代背景下一个重要的领域。这个“Python快速实战机器学习”系列,用Python代码实践机器学习里面的算法,旨在理论和实践同时进行,快速掌握知识。
HuangWeiAI
2019/10/28
5420
Python快速实战机器学习(4) 逻辑回归
Python机器学习(1)-- 自己设计一个感知机(Perceptron)分类算法
红色石头
2017/12/28
2.1K0
Python机器学习(1)-- 自己设计一个感知机(Perceptron)分类算法
机器学习(7)之感知机python实现
关键字全网搜索最新排名 【机器学习算法】:排名第一 【机器学习】:排名第二 【Python】:排名第三 【算法】:排名第四 感知器PLA是一种最简单,最基本的线性分类算法(二分类)。其前提是数据本身是
昱良
2018/04/04
1.6K0
机器学习(7)之感知机python实现
手撸机器学习算法 - 多项式回归
事实上与线性回归相比,多项式回归没有增加任何需要推导的东西,唯一增加的是对原始数据进行多项式特征转换,这有点类似我们在非线性问题中对特征的处理:将
HoLoong
2021/06/21
6050
手撸机器学习算法 - 多项式回归
Python数据挖掘算法入门与实践
数据挖掘是一个通过对大量数据进行清理和处理,以发现其中隐藏的信息和模式的过程。简单来说,它是从大量数据中提取或“挖掘”知识的过程,也称为知识发现。
算法进阶
2024/02/17
1.1K0
Python数据挖掘算法入门与实践
逻辑回归 使用Numpy实现逻辑回归
小小程序员
2023/12/02
3750
逻辑回归 使用Numpy实现逻辑回归
《统计学习方法》第 2 章 感知机 可视化
假设训练数据集是线性可分的 感知机学习的目标是求得一个能够将训练集正实例点和负实例点完全正确分开的分离超平面。为了找出这样的超平面,即确定感知机模型参数
iOSDevLog
2019/06/11
4630
《统计学习方法》第 2 章 感知机 可视化
二分类问题的解决利器:逻辑回归算法详解(一)
其中,P ( Y = 1 ∣ X ) P(Y=1|X)P(Y=1∣X) 表示在给定输入特征X的条件下,目标变量Y等于1的概率。β 0 , β 1 , … , β n \beta_0, \beta_1, \ldots, \beta_nβ0​,β1​,…,βn​ 是模型的权重参数,X 1 , X 2 , … , X n X_1, X_2, \ldots, X_nX1​,X2​,…,Xn​ 是输入特征。
小馒头学Python
2023/11/24
7800
二分类问题的解决利器:逻辑回归算法详解(一)
【机器学习-监督学习】逻辑斯谛回归
  在介绍了机器学习中相关的基本概念和技巧后,本章我们继续讲解参数化模型中的线性模型。有了前文的基础,我们可以先来对KNN算法和线性回归进行比较,进一步回答“什么是参数化模型”这一问题。对于机器学习算法来说,其目标通常可以抽象为得到某个从输入空间到输出空间的映射
Francek Chen
2025/01/22
1770
【机器学习-监督学习】逻辑斯谛回归
相关推荐
手撸机器学习算法 - 线性回归
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
本文部分代码块支持一键运行,欢迎体验
本文部分代码块支持一键运行,欢迎体验