首页 > 其他分享 >神经网络极简入门

神经网络极简入门

时间:2024-05-07 09:59:39浏览次数:25  
标签:极简 入门 self Neuron 神经网络 np 数据 神经元

神经网络是深度学习的基础,正是深度学习的兴起,让停滞不前的人工智能再一次的取得飞速的发展。

其实神经网络的理论由来已久,灵感来自仿生智能计算,只是以前限于硬件的计算能力,没有突出的表现,
直至谷歌的AlphaGO的出现,才让大家再次看到神经网络相较于传统机器学习的优异表现。

本文主要介绍神经网络中的重要基础概念,然后基于这些概念手工实现一个简单的神经网络。
希望通过理论结合实践的方式让大家更容易的理解神经网络。

1. 神经网络是什么

神经网络就像人脑一样,整体看上去非常复杂,但是其基础组成部分并不复杂。
其组成部分中最重要的就是神经元neural),sigmod函数layer)。

1.1. 神经元

神经元(neural)是神经网络最基本的元素,一个神经元包含3个部分:

  • 获取输入:获取多个输入的数据
  • 数学处理:对输入的数据进行数学计算
  • 产生输出:计算后多个输入数据变成一个输出数据

image.png
从上图中可以看出,神经元中的处理有2个步骤。
第一个步骤:从蓝色框变成红色框,是对输入的数据进行加权计算后合并为一个值(N)。
\(N = x_1w_1 + x_2w_2\) 其中,\(w_1,w_2\)分别是输入数据\(x_1,x_2\)的权重。
一般在计算\(N\)的过程中,除了权重,还会加上一个偏移参数\(b\),最终得到:
\(N = x_1w_1 + x_2w_2+b\)

第二个步骤:从红色框变成绿色框,通过sigmoid函数是对N进一步加工得到的神经元的最终输出(M)。

1.2. sigmoid函数

sigmoid函数也被称为S函数,因为的形状类似S形
image.png
它是神经元中的重要函数,能够将输入数据的值映射到\((0,1)\)之间。
最常用的sigmoid函数是 \(f(x)=\frac{1}{1+e^{-x}}\),当然,不是只有这一种sigmoid函数。

至此,神经元通过两个步骤,就把输入的多个数据,转换为一个\((0,1)\)之间的值。

1.3. 层

多个神经元可以组合成一层,一个神经网络一般包含一个输入层和一个输出层,以及多个隐藏层。
image.png
比如上图中,有2个隐藏层,每个隐藏层中分别有4个和2个神经元。
实际的神经网络中,隐藏层数量和其中的神经元数量都是不固定的,根据模型实际的效果来进行调整。

1.4. 网络

通过神经元和层的组合就构成了一个网络,神经网络的名称由此而来。
神经网络可大可小,可简单可复杂,不过,太过简单的神经网络模型效果一般不会太好。

因为一只果蝇就有10万个神经元,而人类的大脑则有大约1000亿个神经元,
这就是为什么训练一个可用的神经网络模型需要庞大的算力,这也是为什么神经网络的理论1943年就提出了,
但是基于深度学习的AlphaGO却诞生于2015年

2. 实现一个神经网络

了解上面的基本概念只能形成一个感性的认知。
下面通过自己动手实现一个最简单的神经网络,来进一步认识神经元sigmoid函数以及隐藏层是如何发挥作用的。

2.1. 准备数据

数据使用sklearn库中经典的鸢尾花数据集,这个数据集中有3个分类的鸢尾花,每个分类50条数据。
为了简化,只取其中前100条数据来使用,也就是取2个分类的鸢尾花数据。

from sklearn.datasets import load_iris

ds = load_iris(as_frame=True, return_X_y=True)
data = ds[0].iloc[:100]
target = ds[1][:100]

print(data)
print(target)

image.png
变量data100条数据,每条数据包含4个属性,分别是花萼的宽度和长度,花瓣的宽度和长度。

image.png
变量target中也是100条数据,只有0和1两种值,表示两种不同种类的鸢尾花。

2.2. 实现神经元

准备好了数据,下面开始逐步实现一个简单的神经网络。
首先,实现最基本的单元--神经元
本文第一节中已经介绍了神经元中主要的2个步骤,分别计算出\(N\)和\(M\)。
image.png
计算\(N\)时,依据每个输入元素的权重(\(w_1,w_2\))和整体的偏移\(b\);
计算\(M\)时,通过sigmoid函数。

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

@dataclass
class Neuron:
    weights: list[float] = field(default_factory=lambda: [])
    bias: float = 0.0
    N: float = 0.0
    M: float = 0.0

    def compute(self, inputs):
        self.N = np.dot(self.weights, inputs) + self.bias
        self.M = sigmoid(self.N)
        return self.M

上面的代码中,Neuron类表示神经元,这个类有4个属性:
其中属性weightsbias是计算\(N\)时的权重和偏移;
属性NM分别是神经元中两步计算的结果。

Neuron类的compute方法根据输入的数据计算神经元的输出。

2.3. 实现神经网络

神经元实现之后,下面就是构建神经网络。
我们的输入数据是带有4个属性(花萼的宽度和长度,花瓣的宽度和长度)的鸢尾花数据,
所以神经网络的输入层有4个值(\(x_1,x_2,x_3,x_4\))。

为了简单起见,我们的神经网络只构建一个隐藏层,其中包含3个神经元
最后就是输出层,输出层最后输出一个值,表示鸢尾花的种类。

由此形成的简单神经网络如下图所示:
image.png

实现的代码:

@dataclass
class MyNeuronNetwork:
    HL1: Neuron = field(init=False)
    HL2: Neuron = field(init=False)
    HL3: Neuron = field(init=False)
    O1: Neuron = field(init=False)

    def __post_init__(self):
        self.HL1 = Neuron()
        self.HL1.weights = np.random.dirichlet(np.ones(4))
        self.HL1.bias = np.random.normal()

        self.HL2 = Neuron()
        self.HL2.weights = np.random.dirichlet(np.ones(4))
        self.HL2.bias = np.random.normal()

        self.HL3 = Neuron()
        self.HL3.weights = np.random.dirichlet(np.ones(4))
        self.HL3.bias = np.random.normal()

        self.O1 = Neuron()
        self.O1.weights = np.random.dirichlet(np.ones(3))
        self.O1.bias = np.random.normal()

    def compute(self, inputs):
        m1 = self.HL1.compute(inputs)
        m2 = self.HL2.compute(inputs)
        m3 = self.HL3.compute(inputs)

        output = self.O1.compute([m1, m2, m3])
        return output

MyNeuronNetwork类是自定义的神经网络,其中的属性是4个神经元
HL1HL2HL3隐藏层的3个神经元;O1输出层的神经元。

__post__init__函数是为了初始化各个神经元。
因为输入层是4个属性(\(x_1,x_2,x_3,x_4\)),所以神经元HL1HL2HL3weights初始化为4个随机数组成的列表,
偏移(bias)用一个随时数来初始化。

对于神经元O1,它的输入是隐藏层的3个神经元,所以它的weights初始化为3个随机数组成的列表,
偏移(bias)还是用一个随时数来初始化。

最后还有一个compute函数,这个函数描述的就是整个神经网络的计算过程。
首先,根据输入层(\(x_1,x_2,x_3,x_4\))的数据计算隐藏层的神经元(HL1HL2HL3);
然后,以隐藏层的神经元(HL1HL2HL3)的输出作为输出层的神经元(O1)的输入,并将O1的计算结果作为整个神经网络的输出。

2.4. 训练模型

上面的神经网络中各个神经元的中的参数(主要是weightsbias)都是随机生成的,
所以直接使用这个神经网络,效果一定不会很好。
所以,我们需要给神经网络(MyNeuronNetwork类)加一个训练函数,用来训练神经网络中各个神经元的参数(也就是个各个神经元中的weightsbias)。

@dataclass
class MyNeuronNetwork:
    # 略...

    def train(self, data: pd.DataFrame, target: pd.Series):
        ## 使用 随机梯度下降算法来训练
        pass

上面的train函数有两个参数data(训练数据)和target(训练数据的标签)。
我们使用随机梯度下降算法来训练模型的参数。
这里略去了具体的代码,完整的代码可以在文章的末尾下载。

此外,再实现一个预测函数predict,传入测试数据集,
然后用我们训练好的神经网络模型来预测测试数据集的标签。

@dataclass
class MyNeuronNetwork:
    # 略...
    
    def predict(self, data: pd.DataFrame):

        results = []
        for idx, row in enumerate(data.values):
            pred = self.compute(row)
            results.append(round(pred))

        return results

2.5. 验证模型效果

最后就是验证模型的效果。

def main():
    # 加载数据
    ds = load_iris(as_frame=True, return_X_y=True)

    # 只用前100条数据
    data = ds[0].iloc[:100]
    target = ds[1][:100]

    # 划分训练数据,测试数据
    # test_size=0.2 表示80%作为训练数据,20%作为测试数据
    X_train, X_test, y_train, y_test = train_test_split(data, target, test_size=0.2)

    # 创建神经网络
    nn = MyNeuronNetwork()

    # 用训练数据集来训练模型
    nn.train(X_train, y_train)

    # 检验模型
    # 用训练过的模型来预测测试数据的标签
    results = nn.predict(X_test)
    df = pd.DataFrame()
    df["预测值"] = results
    df["实际值"] = y_test.values
    print(df)

运行结果可以看出,模型的效果还不错,20条测试数据的预测结果都正确。
image.png

3. 总结

本文中的的神经网络示例是为了介绍神经网络的一些基本概念,所以对神经网络做了尽可能的简化,为了方便去手工实现。

而实际环境中的神经网络,不仅神经元的个数,隐藏层的数量极其庞大,而且其计算和训练的方式也很复杂,手工去实现不太可能,
一般会借助TensorFlowKerasPyTorch等等知名的python深度学习库来帮助我们实现。

4. 代码下载

代码量不大,总共也就200行不到,感兴趣的话可以下载后运行试试。
simple_nn.zip: https://url11.ctfile.com/f/45455611-1242350800-e67991?p=6872 (访问密码: 6872)

标签:极简,入门,self,Neuron,神经网络,np,数据,神经元
From: https://www.cnblogs.com/wang_yb/p/18176563

相关文章

  • Docker-DevOps-入门手册(全)
    DockerDevOps入门手册(全)原文:zh.annas-archive.org/md5/A074DB026A63DFD63D361454222593A5译者:飞龙协议:CCBY-NC-SA4.0前言Docker与DevOps概述了容器化的强大力量以及这种创新对开发团队和一般运营的影响。我们还将了解DevOps的真正含义,涉及的原则,以及通过实施Dock......
  • 入门学习Docker部署Vue+NetCore+MsSql
    最近vultr的主机经常忘了续租,导致账号被禁用,主机被删掉每次重新部署都忘了之前怎么弄的,要重新查好多资料每个月6美金的主机XShell连接主机IP先安装docker开启docker服务镜像容器tar文件 saveload dockerimagesdockercommitbuildDockerfilepull仓库 查看......
  • React入门
    React极简入门:从JavaScript到React-知乎(zhihu.com) HTML<!DOCTYPEhtml><html><head><metacharset="utf-8"><title>Mytestpage</title></head><body><h1>这是标题一</h1>......
  • fastadmin快速入门
    配置安装官网下载https://www.fastadmin.net/download.html配置到public目录下面php版本>7.3伪静态如果没有配置伪静态可以访问不到前台<IfModulemod_rewrite.c>Options+FollowSymlinks-MultiviewsRewriteEngineOnRewriteCond%{REQUEST_FILENAME}!-dRe......
  • 二值神经网络对CNN优化
    二值神经网络概念二值神经网络(BinaryNeuralNetworks,BNN)是一种特殊的人工神经网络,在该网络中,权重和激活函数的值被约束为二进制(通常是+1或-1),而不是传统的浮点数。这种二值化的处理可以减少网络模型的存储需求和计算复杂度,从而在某些情况下提高了运行速度和效率。对CNN手写数字......
  • 班级擂台(光荣)榜 - 极简教育小工具
        擂台(光荣)榜是一款高效的工具,能够迅速展示学生在各个时期的总得分排名。用户可以根据左上角的日期搜索特定时间段内班级学生的排名,也可以根据右上角的“本周”、“上周”、“本月”和“上月”快速定位近期学生的综合名次。在主界面的左侧,系统会自动汇总各小组成员的得......
  • kettle从入门到精通 第五十五课 ETL之kettle Excel输入
    1、 Excel输入,MicrosoftExcel输入步骤的作用是从MicrosoftExcel中读取数据,如下图所示:1)Excel输入步骤从文件D:\data\测试数据.xlsx读取数据。2)将数据通过写日志步骤打印出来。2、Excel输入步骤-文件配置 步骤名称:自定义表格类型(引擎):Excel97-2003XLS:这个引擎是JXL软件......
  • kettle从入门到精通 第五十六课 ETL之kettle Microsoft Excel Output
    1、9.4版本的kettle中有两个Excel输出,Excel输出和MicrosoftExcel输出。前者只支持xls格式,后者支持xls和xlsx两种格式,本节课主要讲解步骤MicrosoftExcel输出,如下图所示: 1)、步骤【生成记录】生成两条测试数据,每条数据里面包含id和name字段。 2)步骤【MicrosoftExcelOutput......
  • 快速入门一篇搞定RocketMq-实现微服务实战落地
    1、RocketMq介绍RocketMQ起源于阿里巴巴,最初是为了解决邮件系统的高可靠性和高性能而设计的。在2016年开源分布式消息中间件,并逐渐成为Apache顶级项目。现在是Apache的一个顶级项目,在阿里内部使用非常广泛,已经经过了"双11"这种万亿级的消息流转,性能稳定、高效。官网地址:https://......
  • 入门推荐系统业务的书单
    最近出差在外,为解决吃饭问题,花了不少时间在美团上翻阅当地的美食,从侧面接触了推荐系统。作为职业程序员,恰逢五一假期,因此花了一些时间查阅了一些资料,期望可以进一步了解推荐系统,拓展知识面。公司内部从事推荐系统领域的同事推荐了如下书籍:从零开始构建企业级推荐系统推荐系统......