QQ登录

只需要一步,快速开始

 注册地址  找回密码
查看: 2444|回复: 0
打印 上一主题 下一主题

[其他资源] 人工神经网络——反向传播算法初体验(python实现)

[复制链接]
字体大小: 正常 放大
杨利霞        

5273

主题

82

听众

17万

积分

  • TA的每日心情
    开心
    2021-8-11 17:59
  • 签到天数: 17 天

    [LV.4]偶尔看看III

    网络挑战赛参赛者

    网络挑战赛参赛者

    自我介绍
    本人女,毕业于内蒙古科技大学,担任文职专业,毕业专业英语。

    群组2018美赛大象算法课程

    群组2018美赛护航培训课程

    群组2019年 数学中国站长建

    群组2019年数据分析师课程

    群组2018年大象老师国赛优

    跳转到指定楼层
    1#
    发表于 2022-9-12 18:40 |只看该作者 |倒序浏览
    |招呼Ta 关注Ta
    人工神经网络——反向传播算法初体验(python实现)
    ; H, l0 C9 s! Q9 I* T& z. d8 E' M3 Y) X1 j# c# k
    背景  z: i& U8 C5 {, q, k
    初次接触反向传播算法,根据C语言中文网的站长提供的思路,照着做一遍找一下感觉,其中链接如下3 v( T4 N$ H+ V
    / A' z! a4 X" r$ c/ a; E$ X
    【神经网络分类算法原理详解】
    & d' c, o0 G4 u* P) o: x
    4 `% g5 l) t% k# T$ e& F% V( q; d注意
    ; b3 D  `. g+ G/ [# [站长提供的图片有点小问题,我们更正如下; H1 K" U/ {8 C$ P

    5 B& H7 R- T7 o& m1 i) A: O' [0 ^( V* c9 Y5 y5 o0 o4 z

    # Z4 T1 `) d% n) Z7 v问题  w- H: ~: e3 x+ J+ e
    根据上图所示,我们有已知
    & m/ a1 V* w$ W0 n4 I! j9 w: h9 L* w: ^( |
    #输入层
    , i$ N# h5 X( ^7 e2 f: hi1=0.054 m2 f$ w& R- P* E5 _! j# q$ j
    i2=0.1
    0 x+ s( X0 T" G# W4 N  p+ D/ y/ n8 Y3 o) @& C  E: R
    #输出层" y( i( _/ p7 D
    o1=0.01$ J; f$ k" S  R' f% _' C
    o2=0.99/ h9 i6 @( C) E7 s* E% Y
    这个神经网络是我们假想的,我们假想从输入层[i1,i2]==>>[o1,o2]的过程是这样的6 A( O/ [( ^1 |$ h  O, E1 Q+ ^
    2 G3 ^6 o  |4 x; L
    神经元h1的输入(h1 input 简写为 hi1)=w1*i1+w2*i2+b1: B9 D- z0 `: s+ a8 n
    3 }* @7 j4 I! g# v0 N: V
    神经元h2的输入  (hi2)=w3*i1+w4*i2+b1
    $ C3 \5 z$ A; A  S0 P0 y7 |! ~1 H+ n3 L* t' ^& n% u
    神经元h1接收到输入后,通过非线性转换函数【这里选择Sigmoid函数】变换得到神经元h1的输出
    ; F. L6 A; |. b, c0 I# L' `
    . l2 w, Q) O- A8 p5 g1 p$ K神经元h1的输出  (ho1)=1.0/(1+math.exp((-1)*神经元h1的输入))2 R) ]8 U% d! z* |! m% @* V

    , ^& g( [0 {; z7 ?$ D) e同理! l: ?' i& V4 M0 v$ A* z
    ! b7 p! W1 N2 g* F
    神经元h2的输出  (ho2)=1.0/(1+math.exp((-1)*神经元h2的输入))
    ) j" c2 B9 g9 B
    8 `' x" C" k% C# A3 Q接下来我们再把隐藏层当作输入层,输出层当作隐藏层,类比推出有关神经元o1,神经元o2的一些表达式1 I5 G, R. k% r) @2 \, s8 D# [
    - x3 S  ^5 r8 ]2 Q' `
    神经元o1的输入 (oi1)=w5*ho1+w6*ho2+b2' C/ z0 X& L7 ^3 p

    0 p# ]  X9 p$ C6 U) I神经元o2的输入 (oi2)=w7*ho1+w8*ho2+b2+ T7 D0 U8 ?4 C$ i- X* m" i
    : `, d7 I* E- S; ?+ L
    再经过非线性变换Sigmoid函数得到5 s1 A7 o- K- a" a" {* O
    5 F5 }$ w' a$ K: Z; H8 |1 A
    神经元o1的输出 (oo1)=1.0/(1+math.exp((-1)*oi1))7 o. W  W* y: j

    - \4 Y5 u9 L  G: C: O3 v神经元o2的输出 (oo2)=1.0/(1+math.exp((-1)*oi2))
    ; D. I. y* g2 G6 m1 z, g' R8 o$ n: A! j; b3 v6 v5 M
    我们将得到的神经元o1输出,神经元o2输出跟我们知道的期望值o1,o2进行比对,定义其损失函数为
    9 V" K4 I3 T9 L3 O
    - v9 |( {% t3 P* v0 M; v损失值  ( error 简写为 eo)=((oo1-o1)^2+(oo2-o2)^2)/27 o% _+ j+ f3 R0 u- x

    " u6 M- F: A1 ], J% J由于我们的期望值精确到小数点后两位,损失函数为平方,所以我们仅需让损失容忍度(eo_allow)调整到1e-5即可满足
    2 l- H2 w$ ]6 A9 \( k4 A
    ' X3 Q! n& Q! P+ U) c学习次数 (learning_time 简写为 lt)我们限定最大为10000次
    % f/ Q! Z. [4 G$ N2 k4 N" d; D1 q# x' `% B. t) _' F+ L$ t7 ~8 P* o% \
    学习率 (learning_rate 简写为 lr)我们设定为0.5/ k8 n. I% L" n% o+ f  s

    % E0 f! A6 |1 Q' ]& x" u依次求解代求参数$ [8 @  c+ t4 H+ L0 y; O% P  _
    5 w4 W& Y4 }& |& D
    w1~w8,以及b1,b2
    5 u5 y+ K' L$ w! P
    : E7 a8 t* ?/ g6 L4 y: l' |
    ( I; _% e% w7 z' f  X, t; l; a2 L) L( S0 [
    损失值 (eo) 的偏导数% P- A: b0 X* B  M

    % l% y7 Z# ?  i+ \再更新该参数,更新公式为
    , R0 k; R% {, O4 {9 o5 U3 [- p1 A) t( ?. _5 S7 U8 n' D
    参数_new=参数-学习率*偏导(eo,参数)( Y- y- e8 \4 U% y! ]8 M& G
    随后进入下一轮学习
    % |2 f8 J+ Q% F1 }$ n( H* {. p) c: Y% A$ `
    终止条件(满足其中一个即可停止训练)
    ! U" s! {3 S' D3 g: h  B8 @  i2 u" B8 }0 d% p
    1.学习次数达到上限
    ! o, d4 U8 x: |0 O  }0 d! @
    " n8 k) ]& g' u  o/ K2.损失值达到可容忍的范围
    * m3 K. q: m' \6 S
    1 x' p' K& E# A4 M! l/ Y导数
    6 O" w; z0 z& x* d( v4 ef(x)=1/(1+e^(-x))的导数是
    6 j0 |- _) c. g/ ^( r* S0 b+ Mf'(x)=f(x)*(1-f(x))5 i4 I% M; H% _4 S5 i8 l; K6 }
    源码3 B3 c- Y  V* D0 U* ^$ u
    import math+ Y2 ~6 D3 N" C

    8 z$ W/ L6 D( `! L  {#参考自网址【http://c.biancheng.net/ml_alg/ann-principle.html】
    / _) I9 s( C  Z( n. U- ~+ C#网址中图片有误,请看我博文上的图片2 A3 i: c+ w0 m
    3 H6 ~0 H0 V- H* T% W: B0 d
    #输入层( ]0 Y) {: H) d  S- \7 |
    i1=0.05
    , A( Z. i* t+ n' i3 Vi2=0.1+ K6 W+ c& T! O2 E9 v4 i7 l: M/ h0 [
    #权值参数
    " Y) X# a4 K. {- e" p. j" fw1=0.15
    & Z0 L6 S2 ?& \2 M+ {1 tw2=0.2& Z- |% y* v4 U& b* s
    w3=0.25
    + v7 K* P9 t- r2 w" Z$ Xw4=0.3
    + {3 c8 F8 X7 E% i4 L9 W6 ?7 n+ Q& Ww5=0.41 e8 K' n& c! {
    w6=0.45% G3 E) ]  z3 A$ H7 i. b
    w7=0.5
    6 O# G4 b- T2 C# Dw8=0.55
    & W5 s, ~8 D3 J( B2 O- _. w4 y#输出层标记(即期望值)
    " d8 B& X1 y4 j" @. x2 [7 fo1=0.01
    4 T1 ?% b$ d( A2 M8 K& do2=0.99
    ) }* h* W1 ]3 `4 Y! [; [/ y  K8 H#偏置项参数
    2 Z- D0 ~* |* w! p3 C/ Jb1=0.358 G7 H6 [4 z$ m& g6 c* M6 e  `
    b2=0.6
    $ Y+ K. c$ z2 l, C( [
    * H, _5 m+ o: X- }+ F#学习率% e$ Y+ j$ Y) K/ B  b2 [" M( m6 y
    lr=0.58 y( K: J& p. D+ @
    #学习周期
    9 f: |& m9 e" o7 t" m5 Q& Plt=07 e9 b/ ~: [* h% e5 P
    max_lt=10000, p8 w" K( O, H$ i
    #允许误差
    2 l" ?' w, X  K8 `eo_allow=1e-5. K6 N; d+ T) {  @! Z: @
    + P: ]" i: B* M3 J
    #线性转换
    ' Z9 i9 g: P( t% T- k6 Fdef linear(w_one,w_two,i_one,i_two,b):9 b6 n* V  K( b6 V  Q; a5 z
        return w_one*i_one+w_two*i_two+b
    6 ]9 {% t3 r* h3 [#非线性转换
    8 @2 g# G2 x# |0 ?9 D/ F7 hdef none_linear(i):
    * j4 M/ I$ k( ~( E    return 1.0/(1+math.exp(-i))
    ! y2 z' F' C0 B" y% f2 U# E
    7 }7 k0 g. i+ C. a8 |2 |print("训练开始")7 U( m6 c) |$ b8 @
    #学习周期结束前一直学习1 n9 x  A! X0 T, n+ m) P* g
    while lt<max_lt:
    . L1 J( t5 q/ }! M, x% K    lt+=1# h7 |% P1 P# r: f6 `
        #求h1和h2输入值" J0 X$ v$ C6 g/ V! }( w5 b( Y6 s
        hi1=linear(w1,w2,i1,i2,b1)
    ! N- s6 m% \5 q" _' x& r  A, V6 o    hi2=linear(w3,w4,i1,i2,b1)' Y, _- t# J$ e
        #求h1和h2输出值; c& }( G# C9 ~4 x7 W  e
        ho1=none_linear(hi1)7 l) s6 X' S: x
        ho2=none_linear(hi2)
    - {& u- G; H- d/ X) S    #求o1和o2输入值9 h/ M  _* e6 n9 \
        oi1=linear(w5,w6,ho1,ho2,b2)# i9 O* O. l0 }  L& w3 r3 z
        oi2=linear(w7,w8,ho1,ho2,b2)2 B8 w. s5 l; T% Y" L
        #求o1和o2输出值
    # e8 L# {) |- z1 I. Y    oo1=none_linear(oi1)7 f. F- u5 b' U' k
        oo2=none_linear(oi2)
    * G- N1 O. z7 [% W9 S( ^) X7 [" U
    + q' S0 x9 \/ t- D2 j    #求当前计算总误差
    8 ~3 n" Y/ o, l3 |3 B8 \7 q    eo=(math.pow(oo1-o1,2)+math.pow(oo2-o2,2))/2
    ' |( W4 V9 y/ }; B2 E! R    print(f"第{lt}次训练,当前计算总误差={eo}")- S+ n" [. @7 Q% Z! W7 ?
        #误差已经在允许范围,退出训练8 v$ ^& L0 o* @& V
        if eo<eo_allow:& Q* a( x/ }$ x/ P, X. W2 l  \
            print("误差已经在允许范围,训练结束\n"); O/ V) i3 j1 A; M2 e! I- W& v3 h
            break
    ( r8 w/ K7 k. v" Y$ C" C    #偏导
    , n" s8 o: B0 c6 n. X( J9 n( D    d_eo_oo1=oo1-o1
    * A1 }1 r0 t! h( r5 l    d_eo_oo2=oo2-o25 p$ P. h, a# t, Q4 V$ f+ F2 l
        d_oo1_oi1=oo1*(1-oo1)- |  ?* k! {6 n; A5 n7 q0 D$ [
        d_oo2_oi2=oo2*(1-oo2): ]3 ?! a, _6 s7 m7 |1 ?
        d_eo_oi1=d_eo_oo1*d_oo1_oi1
    ; C1 F' E( G+ j9 b% L    d_eo_oi2=d_eo_oo2*d_oo2_oi2" Y% A% f, c- G+ F/ h
        #求w5_new
    1 i# p# O1 v5 B: B- u  c9 |: `    d_oi1_w5=ho1
    ) g3 b% U& d6 Q6 h4 C! P( p* O    d_eo_w5=d_eo_oi1*d_oi1_w5/ @! l: R6 [5 ~0 a9 @. v
        w5_new=w5-lr*d_eo_w5
    ! `& K9 f; t! ^' K4 ^9 ?0 R  u    #求w6_new1 ?0 |$ K& n# m  l& [) y* {
        d_oi1_w6=ho25 R# m/ M0 O/ A: _4 z
        d_eo_w6=d_eo_oi1*d_oi1_w6( y& \1 Q4 Q4 {+ E- p/ r4 w0 f/ X
        w6_new=w6-lr*d_eo_w6
    ; M6 @2 [' C! T6 ]; p+ ]  ^. b    #求w7_new6 K; H: p5 b8 R  y7 H5 Y3 \
        d_oi2_w7=ho1: I, s0 T" a3 U( e9 e
        d_eo_w7=d_eo_oi2*d_oi2_w78 m% c% A! ]- w6 Z6 H9 Q5 C( X
        w7_new=w7-lr*d_eo_w7( F, K0 e; [  N, C, n. H
        #求w8_new
    : ?2 g" S6 W+ C( {2 o1 }; I) J    d_oi2_w8=ho2
      R; y9 ?' g' z/ \1 \1 d    d_eo_w8=d_eo_oi2*d_oi2_w82 O) k  `4 k: S0 U
        w8_new=w8-lr*d_eo_w8# c$ ]# Q, W& ?
        #求b2_new, Y- q0 U2 ]' O( X
        d_oi1_b2=1/ L! T. f7 z- y9 x0 R+ l
        d_oi2_b2=1
    9 N. Q3 Y+ P1 w+ W6 C" b6 ~    d_eo_b2=d_eo_oi1*d_oi1_b2+d_eo_oi2*d_oi2_b24 U& p9 V- o' M: D* k- G! T$ B$ s
        b2_new=b2-lr*d_eo_b2
    . E3 a( n$ ^  C$ Z. b    d_oi1_ho1=w5
    0 d% r9 e$ x! A1 T' h: J4 C    d_oi1_ho2=w6. i5 i- d# y, A6 i/ k* u. Y
        d_oi2_ho1=w7
    % n( u8 h- G+ I2 _    d_oi2_ho2=w8! p9 _# e" t% z3 y5 e
        d_eo_ho1=d_eo_oi1*d_oi1_ho1+d_eo_oi2*d_oi2_ho1
    , V9 u& z: c$ w* w7 j3 L    d_eo_ho2=d_eo_oi1*d_oi1_ho2+d_eo_oi2*d_oi2_ho2
    % Q& ~4 J& W2 F  S; s    d_ho1_hi1=ho1*(1-ho1)
    : t3 l7 ]+ S7 K$ d) @( W    d_ho2_hi2=ho2*(1-ho2)
    5 k' c1 `# q3 Q' {7 a    d_eo_hi1=d_eo_ho1*d_ho1_hi1
    : @8 t8 J9 I9 h    d_eo_hi2=d_eo_ho2*d_ho2_hi2$ G8 O: j* `! @8 T6 b9 t; \. p  I% X' ?
        #求w1_new2 R8 R- ?# M! g% D# p
        d_hi1_w1=i1* L1 s+ \4 M( C2 f6 q
        d_eo_w1=d_eo_hi1*d_hi1_w12 L. t- f  i: [3 Y( F% k
        w1_new=w1-lr*d_eo_w15 s- i% N0 T4 g, T3 f
        #求w2_new
      l$ }. ^7 Q# ~& f    d_hi1_w2=i24 V, J( H1 L7 ^! U# z: h$ f( B8 f
        d_eo_w2=d_eo_hi1*d_hi1_w2
    : V' o6 I) P3 k0 e3 e    w2_new=w2-lr*d_eo_w2* _2 v" j* W0 o6 N
        #求w3_new
    2 }; Q4 B) j- J) F+ ]* {3 r    d_hi2_w3=i1
    ( {# w# Q# f; ^6 M    d_eo_w3=d_eo_hi2*d_hi2_w33 X' ^4 q( B( v; M5 `
        w3_new=w3-lr*d_eo_w3
    1 ^+ `5 V( Q9 w    #求w4_new5 _% u  }/ X& }( n) e  Y
        d_hi2_w4=i2
      T$ c% G7 c6 g/ q    d_eo_w4=d_eo_hi2*d_hi2_w4
    $ }- K) r# W5 B2 X( {1 _    w4_new=w4-lr*d_eo_w4. H" N1 v% W$ m1 J1 I$ L
        #求b1_new$ B8 l% w3 \, {: k, S6 ~% S
        d_hi1_b1=1
    6 [7 `8 P# h' I    d_hi2_b1=1
    & M: q+ ?( G" _8 k6 J    d_eo_b1=d_eo_hi1*d_hi1_b1+d_eo_hi2*d_hi2_b16 E/ e' p0 x: A3 H
        b1_new=b1-lr*d_eo_b1
    9 Y8 `" }: J- P- R, D1 k    #更新反向传播
    6 A4 ^% n* N0 f. `, k4 ]" X! K    w1=w1_new: H6 h/ H+ x7 H& i6 r1 C
        w2=w2_new
    ' F+ g' M/ w3 v0 _* `5 F    w3=w3_new% ?$ s" m0 U! n' D
        w4=w4_new' A% }2 _; }# v& @  S7 S" j
        b1=b1_new
    4 J  R! o2 d' K7 F$ g    w5=w5_new
    ( a6 b! @' @0 a0 ~7 a    w6=w6_new
    4 Q) T8 C) j# q4 v    w7=w7_new
    : D; W2 B( q; X& i    w8=w8_new
    + y" ]  `8 }) R0 v; [    b2=b2_new
    + R! R, \; i8 F! b1 T. j+ E2 P( F7 jprint(f"当前计算总误差={eo}")3 b/ R5 [" D" p& E
    print(f"w1={w1}\nw2={w2}\nw3={w3}\nw4={w4}\nb1={b1}\n")
    0 z, |+ e! _, l, H, k1 dprint(f"w5={w5}\nw6={w6}\nw7={w7}\nw8={w8}\nb2={b2}\n")# X" u5 Y# _8 R9 @
    print(f"期望值:[{o1},{o2}],预测值:[{oo1},{oo2}]")
    % v, ^# O4 @& T$ t1 B# V' S
    ' a. v+ Y6 b5 x/ h结果% ]9 p5 T5 r! M% q

      ~; a* J5 E9 X! X+ R9 f
    $ g: G& u- o" H结语1 X  A1 d" |& }0 R0 b+ t
    可以看到,在经过七千多次训练之后,我们找到了一组参数满足我们假想的关系,本次人工神经网络训练完成,反向传播算法体验结果良好。0 @( H6 P& R: S- D! q" F( a
    : y; r* U1 C  S! `3 L
    补充: k$ m, o0 Y0 |. |/ P
    程序中d_{a}_{b}格式的变量表示a对b偏导; @6 C( t  u( j5 T2 \/ Z
    ————————————————( w' b; I' X5 m; v- |! G' V
    版权声明:本文为CSDN博主「冰凌呀」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。  G" m% }( |1 K$ A9 h
    原文链接:https://blog.csdn.net/qq_36694133/article/details/1266679547 c- {* ^* Q& n6 ?% N: ?

    1 U+ g$ \/ A2 C: X9 Y$ ^- }! `  V" M0 e! }7 T3 E% j( u8 H
    zan
    转播转播0 分享淘帖0 分享分享0 收藏收藏0 支持支持0 反对反对0 微信微信
    您需要登录后才可以回帖 登录 | 注册地址

    qq
    收缩
    • 电话咨询

    • 04714969085
    fastpost

    关于我们| 联系我们| 诚征英才| 对外合作| 产品服务| QQ

    手机版|Archiver| |繁體中文 手机客户端  

    蒙公网安备 15010502000194号

    Powered by Discuz! X2.5   © 2001-2013 数学建模网-数学中国 ( 蒙ICP备14002410号-3 蒙BBS备-0002号 )     论坛法律顾问:王兆丰

    GMT+8, 2025-8-15 03:51 , Processed in 0.365992 second(s), 50 queries .

    回顶部