日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

【TensorFlow学习笔记:神经网络优化(6讲)】

發(fā)布時間:2023/12/1 编程问答 37 豆豆
生活随笔 收集整理的這篇文章主要介紹了 【TensorFlow学习笔记:神经网络优化(6讲)】 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

目錄

  • 【1】NN復(fù)雜度
  • 【2】指數(shù)衰減學(xué)習(xí)率
  • 【3】激活函數(shù)
    • 優(yōu)秀激活函數(shù)所具有的特點
    • 常見的激活函數(shù)
    • 對于初學(xué)者的建議
  • 【4】損失函數(shù)
  • 【5】緩解過擬合——正則化
  • 【6】參數(shù)優(yōu)化器
    • 【1】SGD
    • 【2】SGDM(SGD基礎(chǔ)上增加了一階動量)
    • 【3】Adagrade(SGD基礎(chǔ)上增加了二階動量)
    • 【4】RMSProp(SGD基礎(chǔ)上增加了二階動量)
    • 【5】Adam(同時結(jié)合SGDM一階動量和RMSProp的二節(jié)動量)
    • 優(yōu)化器對比總結(jié)

【1】NN復(fù)雜度

空間復(fù)雜度:
層數(shù):隱藏層層數(shù)+輸出層
總參數(shù):總w+總b
時間復(fù)雜度:
乘加運算次數(shù)
以下圖為例:總參數(shù)=3x4+4(第一層) +4x2+2(第二層)=26
乘加運算次數(shù)=3x4+4x2=20

【2】指數(shù)衰減學(xué)習(xí)率

已知:學(xué)習(xí)率過小,收斂速度慢。學(xué)習(xí)率過大導(dǎo)致不收斂。
可以先用較大的學(xué)習(xí)率,快速得到較優(yōu)解,然后逐步減小學(xué)習(xí)率,使模型在訓(xùn)練后期穩(wěn)定,例如指數(shù)衰減學(xué)習(xí)率。

指數(shù)衰減學(xué)習(xí)率=初始學(xué)習(xí)率*學(xué)習(xí)率衰減率^(當前輪數(shù)/多少輪衰減一次)

epoch = 40 LR_BASE = 0.2 # 最初學(xué)習(xí)率 LR_DECAY = 0.99 # 學(xué)習(xí)率衰減率 LR_STEP = 1 # 喂入多少輪BATCH_SIZE后,更新一次學(xué)習(xí)率 for epoch in range(epoch): # for epoch 定義頂層循環(huán),表示對數(shù)據(jù)集循環(huán)epoch次,此例數(shù)據(jù)集數(shù)據(jù)僅有1個w,初始化時候constant賦值為5,循環(huán)100次迭代。lr = LR_BASE * LR_DECAY ** (epoch / LR_STEP)

【3】激活函數(shù)

對于線性函數(shù),即使有多個神經(jīng)元首尾相接構(gòu)成深層神經(jīng)網(wǎng)絡(luò),依舊是線性組合,模型表達力不夠。

MP模型比簡化模型多了一個激活函數(shù),它的加入加強了模型的表達力,使得深層網(wǎng)絡(luò)不再是輸入x的線性組合,而且隨著層數(shù)增加提升表達力。

優(yōu)秀激活函數(shù)所具有的特點

非線性:激活函數(shù)非線性時,多層神經(jīng)網(wǎng)絡(luò)可以逼近所有函數(shù)
可微性:優(yōu)化器大多用梯度下降更新參數(shù)
單調(diào)性:當激活函數(shù)是單調(diào)的,能保證單層網(wǎng)絡(luò)的損失函數(shù)是凸函數(shù)
近似恒等性:f(x)約等于x,當參數(shù)初始化為隨機小值時,神經(jīng)網(wǎng)絡(luò)更穩(wěn)定

激活函數(shù)輸出值的范圍:
1、激活函數(shù)輸出為有限值時,權(quán)重對于特征的影響會更顯著,基于梯度的優(yōu)化方法更穩(wěn)定
2、激活函數(shù)輸出為無限值時,參數(shù)的初始值對模型的影響特別大,要使用更小的學(xué)習(xí)率

常見的激活函數(shù)

1、sigmoid函數(shù):
函數(shù)公式、函數(shù)圖像與導(dǎo)數(shù)圖像:

調(diào)用方法:tf.nn.sigmoid(x)
特點:
1、易造成梯度消失(輸入的值較大時,梯度就約等于0了)
2、輸出非0均值,收斂慢(我們希望輸入每層網(wǎng)絡(luò)的特征是以0為均值的小數(shù))
3、冪運算復(fù)雜,訓(xùn)練時間長

神經(jīng)網(wǎng)絡(luò)最初興起的時候,sigmoid函數(shù)作為激活函數(shù)用的很多,但是近年來用sigmoid函數(shù)的網(wǎng)絡(luò)已經(jīng)很少了。
因為,深層神經(jīng)網(wǎng)絡(luò)更新參數(shù)時,需要從輸出層到輸入層逐層進行鏈式求導(dǎo),而sigmoid函數(shù)導(dǎo)數(shù)的輸出范圍是(0,0.25],鏈式求導(dǎo)需要多層導(dǎo)數(shù)連續(xù)相乘,這樣最終導(dǎo)致輸出為0,造成梯度消失,參數(shù)無法繼續(xù)更新。

2、Tanh函數(shù):
調(diào)用方法:tf.math.tanh(x)
特點:
1、易造成梯度消失
2、輸出0均值
3、冪運算復(fù)雜,訓(xùn)練時間長
函數(shù)公式、函數(shù)圖像與導(dǎo)數(shù)圖像:

3、Relu函數(shù):
函數(shù)公式、函數(shù)圖像與導(dǎo)數(shù)圖像:

調(diào)用方法:tf.nn.relu(x) 優(yōu)點: 1、在正區(qū)間解決了梯度消失的問題 2、只需要判斷輸入是否大于0,計算速度快 3、收斂速度遠快于sigmoid和tanh 4、具備近似恒等性 缺點: 1、輸出非0均值,瘦收斂慢 2、Dead ReIU問題,某些神經(jīng)元可能永遠無法被激活,導(dǎo)致相應(yīng)的參數(shù)永遠無法更新

送入激活函數(shù)的輸入特征是負數(shù)時,激活函數(shù)輸出是0,反向傳輸梯度是0,經(jīng)過relu函數(shù)的負數(shù)特征過多導(dǎo)致神經(jīng)元死亡,我們可以改進隨機初始化,避免過多負數(shù)特征傳入,也可以通過設(shè)置更小的學(xué)習(xí)率,減少參數(shù)分布的巨大變化,避免訓(xùn)練中產(chǎn)生過多負數(shù)特征

4、Leaky Relu函數(shù):
函數(shù)公式、函數(shù)圖像與導(dǎo)數(shù)圖像:

調(diào)用方法:tf.nn.leaky_relu(x)
理論上來說,leaky relu具有relu的所有優(yōu)點,外加不會有deadrelu問題,但是在實際操作中,并沒有完全證明leaky relu總好于relu

對于初學(xué)者的建議

1、首選relu激活函數(shù)
2、學(xué)習(xí)率設(shè)置較小值
3、輸入特征標準化,讓輸入特征滿足以0為均值,1為標準差的正態(tài)分布
4、初始參數(shù)中心化,讓隨機生成的參數(shù)滿足0位均值,sqrt(2/當前層輸入特征個數(shù))為標準差的正態(tài)分布

【4】損失函數(shù)

NN優(yōu)化目標:loss最小
常用三種損失函數(shù):1、mse(均方差)2、自定義3、ce(交叉熵)
1、mse(均方差)
mse調(diào)用方式:

loss_mse =tf.reduce_mean(tf.square(y_-y))

預(yù)測酸奶代碼:

import tensorflow as tf import numpy as npSEED = 23455rdm = np.random.RandomState(seed=SEED) # 生成[0,1)之間的隨機數(shù) x = rdm.rand(32, 2) y_ = [[x1 + x2 + (rdm.rand() / 10.0 - 0.05)] for (x1, x2) in x] # 生成噪聲[0,1)/10=[0,0.1); [0,0.1)-0.05=[-0.05,0.05) x = tf.cast(x, dtype=tf.float32)w1 = tf.Variable(tf.random.normal([2, 1], stddev=1, seed=1))epoch = 15000 lr = 0.002for epoch in range(epoch):with tf.GradientTape() as tape:y = tf.matmul(x, w1)loss_mse = tf.reduce_mean(tf.square(y_ - y))grads = tape.gradient(loss_mse, w1)w1.assign_sub(lr * grads)if epoch % 500 == 0:print("After %d training steps,w1 is " % (epoch))print(w1.numpy(), "\n") print("Final w1 is: ", w1.numpy())

生成的系數(shù)確實約等于1
2、自定義損失函數(shù)
以銷量預(yù)測為例:
均方誤差損失函數(shù)默認認為銷量預(yù)測多了、少了,造成的損失是一樣的,其實不然。
預(yù)測多了:損失成本
預(yù)測少了:損失利潤
若利潤不等于成本,則mse產(chǎn)生的loss無法利益最大化!
可以把損失定義為一個分段函數(shù)

loss_zdy=tf,reduce_sum(tf.where(tf.greater(y,y_),COST(y-y_),PROFIT(y_-y)))
如:預(yù)測酸奶銷量,酸奶成本(COST)1元,酸奶利潤(PROFIT)99元。
預(yù)測少了損失利潤99元,大于預(yù)測多了損失成本1元。
預(yù)測少了損失大,希望生成的預(yù)測函數(shù)往多了預(yù)測。
預(yù)測酸奶代碼:(修改損失函數(shù))

import tensorflow as tf import numpy as npSEED = 23455 COST = 1 PROFIT = 99rdm = np.random.RandomState(SEED) x = rdm.rand(32, 2) y_ = [[x1 + x2 + (rdm.rand() / 10.0 - 0.05)] for (x1, x2) in x] # 生成噪聲[0,1)/10=[0,0.1); [0,0.1)-0.05=[-0.05,0.05) x = tf.cast(x, dtype=tf.float32)w1 = tf.Variable(tf.random.normal([2, 1], stddev=1, seed=1))epoch = 10000 lr = 0.002for epoch in range(epoch):with tf.GradientTape() as tape:y = tf.matmul(x, w1)loss = tf.reduce_sum(tf.where(tf.greater(y, y_), (y - y_) * COST, (y_ - y) * PROFIT))grads = tape.gradient(loss, w1)w1.assign_sub(lr * grads)if epoch % 500 == 0:print("After %d training steps,w1 is " % (epoch))print(w1.numpy(), "\n") print("Final w1 is: ", w1.numpy())# 自定義損失函數(shù) # 酸奶成本1元, 酸奶利潤99元 # 成本很低,利潤很高,人們希望多預(yù)測些,生成模型系數(shù)大于1,往多了預(yù)測

生成的系數(shù)確實都大于1
3、ce(交叉熵)
調(diào)用方式:tf.losses.categorical_crossentropy(y_, y)

import tensorflow as tfloss_ce1 = tf.losses.categorical_crossentropy([1, 0], [0.6, 0.4]) loss_ce2 = tf.losses.categorical_crossentropy([1, 0], [0.8, 0.2]) print("loss_ce1:", loss_ce1) print("loss_ce2:", loss_ce2)# 交叉熵損失函數(shù)

一般來說,輸出先通過softmax函數(shù)使之符合概率分布,再計算y與y_的交叉熵損失函數(shù),TensorFlow提供了同時計算的函數(shù)
tf.nn.softmax_cross_entropy_with_logits(y_, y)

# softmax與交叉熵損失函數(shù)的結(jié)合 import tensorflow as tf import numpy as npy_ = np.array([[1, 0, 0], [0, 1, 0], [0, 0, 1], [1, 0, 0], [0, 1, 0]]) y = np.array([[12, 3, 2], [3, 10, 1], [1, 2, 5], [4, 6.5, 1.2], [3, 6, 1]]) y_pro = tf.nn.softmax(y) loss_ce1 = tf.losses.categorical_crossentropy(y_,y_pro) loss_ce2 = tf.nn.softmax_cross_entropy_with_logits(y_, y)print('分步計算的結(jié)果:\n', loss_ce1) print('結(jié)合計算的結(jié)果:\n', loss_ce2)

【5】緩解過擬合——正則化

為什么正則化可以化解過擬合,先看看下面兩個視頻和講解吧:
過擬合
正則化如何運行
正則化不舍棄特征,而是減少了特征變量的量級,從而簡化假設(shè)模型。由于變量過多,我們事先并不知曉每個變量對結(jié)果的相關(guān)程度,也就是說我們不知道該縮小哪些參數(shù),我們選擇縮小所有參數(shù),也就是給所有參數(shù)加上懲罰項(除了theta0變量)。

正則化參數(shù)λ用來控制兩個不同目標之間的取舍:
1、更好地擬合訓(xùn)練數(shù)據(jù)
2、保持參數(shù)盡量地小
λ過大同樣也會造成欠擬合的現(xiàn)象。

欠擬合解決方法:
1、增加輸入特征項
2、增加網(wǎng)絡(luò)參數(shù)
3、減少正則化參數(shù)
過擬合的解決方法:
1、數(shù)據(jù)清洗
2、增大訓(xùn)練集
3、采用正則化
4、增大正則化參數(shù)


示例:利用神經(jīng)網(wǎng)絡(luò)區(qū)分藍色點和紅色點

思路:
1、先用神經(jīng)網(wǎng)絡(luò)擬合出數(shù)據(jù)x1,x2,y_c的函數(shù)關(guān)系
2、生成網(wǎng)格覆蓋這些點
3、將網(wǎng)格中坐標送入訓(xùn)練好的神經(jīng)網(wǎng)絡(luò)
4、網(wǎng)絡(luò)為每個坐標輸出一個預(yù)測值
5、將神經(jīng)網(wǎng)絡(luò)輸出為0.5的預(yù)測值的線標出顏色,這線就是區(qū)分線
分別輸出不正則化和正則化的效果,觀察效果

左側(cè)是正則化之前的,右側(cè)是正則化之后的。

1層隱藏層,4個神經(jīng)元 1層隱藏層,4個神經(jīng)元
1層隱藏層,22個神經(jīng)元1層隱藏層,22個神經(jīng)元
1層隱藏層,40個神經(jīng)元1層隱藏層,40個神經(jīng)元

很明顯地可以看出,加入L2正則化后的曲線更加平緩。有效緩解了過擬合。

【6】參數(shù)優(yōu)化器

推薦鏈接
【基礎(chǔ)算法】神經(jīng)網(wǎng)絡(luò)參數(shù)優(yōu)化器https://zhuanlan.zhihu.com/p/97873519
MOOC神經(jīng)網(wǎng)絡(luò)參數(shù)優(yōu)化器
參數(shù)優(yōu)化器總體公式:

【1】SGD

公式:
code:

# 實現(xiàn)梯度更新 w1 = w1 - lr * w1_grad b = b - lr * b_grad w1.assign_sub(lr * grads[0]) # 參數(shù)w1自更新 b1.assign_sub(lr * grads[1]) # 參數(shù)b自更新

【2】SGDM(SGD基礎(chǔ)上增加了一階動量)

公式:

mt表示各時刻梯度方向的指數(shù)滑動平均值,表征了過去一段時間的平均值。β是接近1的超參數(shù),一般等于0.9
code:

m_w, m_b = 0, 0 beta = 0.9# sgd-momentun m_w = beta * m_w + (1 - beta) * grads[0] m_b = beta * m_b + (1 - beta) * grads[1] w1.assign_sub(lr * m_w) b1.assign_sub(lr * m_b)

【3】Adagrade(SGD基礎(chǔ)上增加了二階動量)

公式:

code:

v_w, v_b = 0, 0 # adagrad v_w += tf.square(grads[0]) v_b += tf.square(grads[1]) w1.assign_sub(lr * grads[0] / tf.sqrt(v_w)) b1.assign_sub(lr * grads[1] / tf.sqrt(v_b))

【4】RMSProp(SGD基礎(chǔ)上增加了二階動量)

公式:

v_w, v_b = 0, 0 beta = 0.9 # rmsprop v_w = beta * v_w + (1 - beta) * tf.square(grads[0]) v_b = beta * v_b + (1 - beta) * tf.square(grads[1]) w1.assign_sub(lr * grads[0] / tf.sqrt(v_w)) b1.assign_sub(lr * grads[1] / tf.sqrt(v_b))

【5】Adam(同時結(jié)合SGDM一階動量和RMSProp的二節(jié)動量)

公式:

code:

m_w, m_b = 0, 0 v_w, v_b = 0, 0 beta1, beta2 = 0.9, 0.999 delta_w, delta_b = 0, 0 global_step = 0 # adam m_w = beta1 * m_w + (1 - beta1) * grads[0] m_b = beta1 * m_b + (1 - beta1) * grads[1] v_w = beta2 * v_w + (1 - beta2) * tf.square(grads[0]) v_b = beta2 * v_b + (1 - beta2) * tf.square(grads[1])m_w_correction = m_w / (1 - tf.pow(beta1, int(global_step))) m_b_correction = m_b / (1 - tf.pow(beta1, int(global_step))) v_w_correction = v_w / (1 - tf.pow(beta2, int(global_step))) v_b_correction = v_b / (1 - tf.pow(beta2, int(global_step)))w1.assign_sub(lr * m_w_correction / tf.sqrt(v_w_correction)) b1.assign_sub(lr * m_b_correction / tf.sqrt(v_b_correction))

優(yōu)化器對比總結(jié)

優(yōu)化器對比(lr=0.1 epoch=500 batch=32)




總結(jié)

以上是生活随笔為你收集整理的【TensorFlow学习笔记:神经网络优化(6讲)】的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。