精品国产人成在线_亚洲高清无码在线观看_国产在线视频国产永久2021_国产AV综合第一页一个的一区免费影院黑人_最近中文字幕MV高清在线视频

0
  • 聊天消息
  • 系統消息
  • 評論與回復
登錄后你可以
  • 下載海量資料
  • 學習在線課程
  • 觀看技術視頻
  • 寫文章/發帖/加入社區
會員中心
創作中心

完善資料讓更多小伙伴認識你,還能領取20積分哦,立即完善>

3天內不再提示

過擬合的概念和用幾種用于解決過擬合問題的正則化方法

zhKF_jqr_AI ? 來源:未知 ? 作者:李倩 ? 2018-04-27 15:23 ? 次閱讀

在日常工作、學習中,數據科學家最常遇到的問題之一就是過擬合。你是否曾有過這樣一個模型,它在訓練集上表現優秀,在測試集上卻一塌糊涂。你是否也曾有過這樣的經歷,當你參加建模競賽時,從跑分上看你的模型明明應該高居榜首,但在賽方公布的成績榜上,它卻名落孫山,遠在幾百名之后。如果你有過類似經歷,那本文就是專為寫的——它會告訴你如何避免過擬合來提高模型性能。

在這篇文章中,我們將詳細講述過擬合的概念和用幾種用于解決過擬合問題的正則化方法,并輔以Python案例講解,以進一步鞏固這些知識。注意,本文假設讀者具備一定的神經網絡、Keras實現的經驗。

什么是正則化

在深入探討這個話題之前,請看一下這張圖片:

每次談及過擬合,這張圖片就會時不時地被拉出來“鞭尸”。如上圖所示,剛開始的時候,模型還不能很好地擬合所有數據點,即無法反映數據分布,這時它是欠擬合的。而隨著訓練次數增多,它慢慢找出了數據的模式,能在盡可能多地擬合數據點的同時反映數據趨勢,這時它是一個性能較好的模型。在這基礎上,如果我們繼續訓練,那模型就會進一步挖掘訓練數據中的細節和噪聲,為了擬合所有數據點“不擇手段”,這時它就過擬合了。

換句話說,從左往右看,模型的復雜度逐漸提高,在訓練集上的預測錯誤逐漸減少,但它在測試集上的錯誤率卻呈現一條下凸曲線。

如果你之前構建過神經網絡,想必你已經得到了這個教訓:網絡有多復雜,過擬合就有多容易。為了使模型在擬合數據的同時更具推廣性,我們可以用正則化對學習算法做一些細微修改,從而提高模型的整體性能。

正則化和過擬合

過擬合和神經網絡的設計密切相關,因此我們先來看一個過擬合的神經網絡:

如果你之前閱讀過我們的從零學習:從Python和R理解和編碼神經網絡(完整版),或對神經網絡正則化概念有初步了解,你應該知道上圖中帶箭頭的線實際上都帶有權重,而神經元是儲存輸入輸出的地方。為了公平起見,也就是為了防止網絡在優化方向上過于放飛自我,這里我們還需要加入一個先驗——正則化懲罰項,用來懲罰神經元的加權矩陣。

如果我們設的正則化系數很大,導致一些加權矩陣的值幾乎為零——那最后我們得到的是一個更簡單的線性網絡,它很可能是欠擬合的。

因此這個系數并不是越大越好。我們需要優化這個正則化系數的值,以便獲得一個良好擬合的模型,如下圖所示。

深度學習中的正則化

L2和L1正則化

L1和L2是最常見的正則化方法,它們的做法是在代價函數后面再加上一個正則化項。

代價函數 = 損失(如二元交叉熵) + 正則化項

由于添加了這個正則化項,各權值被減小了,換句話說,就是神經網絡的復雜度降低了,結合“網絡有多復雜,過擬合就有多容易”的思想,從理論上來說,這樣做等于直接防止過擬合(奧卡姆剃刀法則)。

當然,這個正則化項在L1和L2里是不一樣的。

對于L2,它的代價函數可表示為:

這里λ就是正則化系數,它是一個超參數,可以被優化以獲得更好的結果。對上式求導后,權重w前的系數為1?ηλ/m,因為η、λ、m都是正數,1?ηλ/m小于1,w的趨勢是減小,所以L2正則化也被稱為權重衰減。

而對于L1,它的代價函數可表示為:

和L2不同,這里我們懲罰的是權重w的絕對值。對上式求導后,我們得到的等式里包含一項-sgn(w),這意味著當w是正數時,w減小趨向于0;當w是負數時,w增大趨向于0。所以L1的思路就是把權重往0靠,從而降低網絡復雜度。

因此當我們想要壓縮模型時,L1的效果會很好,但如果只是簡單防止過擬合,一般情況下還是會用L2。在Keras中,我們可以直接調用regularizers在任意層做正則化。

例:在全連接層使用L2正則化的代碼:

from keras import regularizers

model.add(Dense(64, input_dim=64,

kernel_regularizer=regularizers.l2(0.01)

注:這里的0.01是正則化系數λ的值,我們可以通過網格搜索對它做進一步優化。

Dropout

Dropout稱得上是正則化方法中最有趣的一種,它的效果也很好,所以是深度學習領域常用的方法之一。為了更好地解釋它,我們先假設我們的神經網絡長這樣:

那么Dropout到底drop了什么?我們來看下面這幅圖:在每次迭代中,它會隨機選擇一些神經元,并把它們“滿門抄斬”——把神經元連同相應的輸入輸出一并“刪除”。

比起L1和L2對代價函數的修改,Dropout更像是訓練網絡的一種技巧。隨著訓練進行,神經網絡在每一次迭代中都會忽視一些(超參數,常規是一半)隱藏層/輸入層的神經元,這就導致不同的輸出,其中有的是正確的,有的是錯誤的。

這個做法有點類似集成學習,它能更多地捕獲更多的隨機性。集成學習分類器通常比單一分類器效果更好,同樣的,因為網絡要擬合數據分布,所以Dropout后模型大部分的輸出肯定是正確的,而噪聲數據影響只占一小部分,不會對最終結果造成太大影響。

由于這些因素,當我們的神經網絡較大且隨機性更多時,我們一般用Dropout。

在Keras中,我們可以使用keras core layer實現dropout。下面是它的Python代碼:

from keras.layers.core importDropout

model = Sequential([

Dense(output_dim=hidden1_num_units, input_dim=input_num_units, activation='relu'),

Dropout(0.25),

Dense(output_dim=output_num_units, input_dim=hidden5_num_units, activation='softmax'),

])

注:這里我們把0.25設為Dropout的超參數(每次“刪”1/4),我們可以通過網格搜索對它做進一步優化。

數據增強

既然過擬合是模型對數據集中噪聲和細節的過度捕捉,那么防止過擬合最簡單的方法就是增加訓練數據量。但是在機器學習任務中,增加數據量并不是那么容易實現的,因為搜集、標記數據的成本太高了。

假設我們正在處理的一些手寫數字圖像,為了擴大訓練集,我們能采取的方法有——旋轉、翻轉、縮小/放大、位移、截取、添加隨機噪聲、添加畸變等。下面是一些處理過的圖:

這些方式就是數據增強。從某種意義上來說,機器學習模型的性能是靠數據量堆出來的,因此數據增強可以為模型預測的準確率提供巨大提升。有時為了改進模型,這也是一種必用的技巧。

在Keras中,我們可以使用ImageDataGenerator執行所有這些轉換,它提供了一大堆可以用來預處理訓練數據的參數列表。以下是實現它的示例代碼:

from keras.preprocessing.image importImageDataGenerator

datagen = ImageDataGenerator(horizontal flip=True)

datagen.fit(train)

早停法

這是一種交叉驗證策略。訓練前,我們從訓練集中抽出一部分作為驗證集,隨著訓練的進行,當模型在驗證集上的性能越來越差時,我們立即手動停止訓練,這種提前停止的方法就是早停法。

在上圖中,我們應該在虛線位置就停止訓練,因為在那之后,模型就開始過擬合了。

在Keras中,我們可以調用callbacks函數提前停止訓練,以下是它的示例代碼:

from keras.callbacks importEarlyStopping

EarlyStopping(monitor='val_err', patience=5)

在這里,monitor指的是需要監控的epoch數量;val_err表示驗證錯誤(validation error)。

patience表示經過5個連續epoch后模型預測結果沒有進一步改善。結合上圖進行理解,就是在虛線后,模型每訓練一個epoch就會有更高的驗證錯誤(更低的驗證準確率),因此連續訓練5個epoch后,它會提前停止訓練。

注:有一種情況是當模型訓練5個epoch后,它的驗證準確率可能會提高,因此選取超參數時我們要小心。

用keras實例研究MNIST數據

數據集:datahack.analyticsvidhya.com/contest/practice-problem-identify-the-digits/

學了這么多正則化方法,現在我們就要開始動手實踐了。在這個案例中,我們用的是Analytics Vidhya的數字識別數據集。

我們先導幾個基本庫:

%pylab inline

import numpy as np

import pandas as pd

from scipy.misc import imread

from sklearn.metrics import accuracy_score

from matplotlib import pyplot

import tensorflow as tf

import keras

# 阻止潛在的隨機性

seed = 128

rng = np.random.RandomState(seed)

然后加載數據集:

root_dir = os.path.abspath('/Users/shubhamjain/Downloads/AV/identify the digits/')

data_dir = os.path.join(root_dir, 'data')

sub_dir = os.path.join(root_dir, 'sub')

## 只讀取訓練文件

train = pd.read_csv(os.path.join(data_dir, 'Train', 'train.csv'))

train.head()

檢查一下圖像:

img_name = rng.choice(train.filename)

filepath = os.path.join(data_dir, 'Train', 'Images', 'train', img_name)

img = imread(filepath, flatten=True)

pylab.imshow(img, cmap='gray')

pylab.axis('off')

pylab.show()

# 在numpy數組中存儲圖像

temp = []

for img_name in train.filename:

image_path = os.path.join(data_dir, 'Train', 'Images', 'train', img_name)

img = imread(image_path, flatten=True)

img = img.astype('float32')

temp.append(img)

x_train = np.stack(temp)

x_train /= 255.0

x_train = x_train.reshape(-1, 784).astype('float32')

y_train = keras.utils.np_utils.to_categorical(train.label.values)

創建驗證數據集(7:3):

split_size = int(x_train.shape[0]*0.7)

x_train, x_test = x_train[:split_size], x_train[split_size:]

y_train, y_test = y_train[:split_size], y_train[split_size:]

構建一個帶有5個隱藏層的簡單神經網絡,每層包含500個神經元:

# 導入keras模塊

from keras.models importSequential

from keras.layers importDense

# define vars

input_num_units = 784

hidden1_num_units = 500

hidden2_num_units = 500

hidden3_num_units = 500

hidden4_num_units = 500

hidden5_num_units = 500

output_num_units = 10

epochs = 10

batch_size = 128

model = Sequential([

Dense(output_dim=hidden1_num_units, input_dim=input_num_units, activation='relu'),

Dense(output_dim=hidden2_num_units, input_dim=hidden1_num_units, activation='relu'),

Dense(output_dim=hidden3_num_units, input_dim=hidden2_num_units, activation='relu'),

Dense(output_dim=hidden4_num_units, input_dim=hidden3_num_units, activation='relu'),

Dense(output_dim=hidden5_num_units, input_dim=hidden4_num_units, activation='relu'),

Dense(output_dim=output_num_units, input_dim=hidden5_num_units, activation='softmax'),

])

先跑10個epoch,快速檢查一下模型性能:

model.compile(loss='categorical_crossentropy', optimizer='adam', metrics=['accuracy'])

trained_model_5d = model.fit(x_train, y_train, nb_epoch=epochs, batch_size=batch_size, validation_data=(x_test, y_test))

L2正則化

from keras import regularizers

model = Sequential([

Dense(output_dim=hidden1_num_units, input_dim=input_num_units, activation='relu',

kernel_regularizer=regularizers.l2(0.0001)),

Dense(output_dim=hidden2_num_units, input_dim=hidden1_num_units, activation='relu',

kernel_regularizer=regularizers.l2(0.0001)),

Dense(output_dim=hidden3_num_units, input_dim=hidden2_num_units, activation='relu',

kernel_regularizer=regularizers.l2(0.0001)),

Dense(output_dim=hidden4_num_units, input_dim=hidden3_num_units, activation='relu',

kernel_regularizer=regularizers.l2(0.0001)),

Dense(output_dim=hidden5_num_units, input_dim=hidden4_num_units, activation='relu',

kernel_regularizer=regularizers.l2(0.0001)),

Dense(output_dim=output_num_units, input_dim=hidden5_num_units, activation='softmax'),

])

model.compile(loss='categorical_crossentropy', optimizer='adam', metrics=['accuracy'])

trained_model_5d = model.fit(x_train, y_train, nb_epoch=epochs, batch_size=batch_size, validation_data=(x_test, y_test))

λ等于0.0001,模型預測準確率更高了!

L1正則化

## l1

model = Sequential([

Dense(output_dim=hidden1_num_units, input_dim=input_num_units, activation='relu',

kernel_regularizer=regularizers.l1(0.0001)),

Dense(output_dim=hidden2_num_units, input_dim=hidden1_num_units, activation='relu',

kernel_regularizer=regularizers.l1(0.0001)),

Dense(output_dim=hidden3_num_units, input_dim=hidden2_num_units, activation='relu',

kernel_regularizer=regularizers.l1(0.0001)),

Dense(output_dim=hidden4_num_units, input_dim=hidden3_num_units, activation='relu',

kernel_regularizer=regularizers.l1(0.0001)),

Dense(output_dim=hidden5_num_units, input_dim=hidden4_num_units, activation='relu',

kernel_regularizer=regularizers.l1(0.0001)),

Dense(output_dim=output_num_units, input_dim=hidden5_num_units, activation='softmax'),

])

model.compile(loss='categorical_crossentropy', optimizer='adam', metrics=['accuracy'])

trained_model_5d = model.fit(x_train, y_train, nb_epoch=epochs, batch_size=batch_size, validation_data=(x_test, y_test))

模型準確率沒有任何提高,PASS!

Dropout

## dropout

from keras.layers.core importDropout

model = Sequential([

Dense(output_dim=hidden1_num_units, input_dim=input_num_units, activation='relu'),

Dropout(0.25),

Dense(output_dim=hidden2_num_units, input_dim=hidden1_num_units, activation='relu'),

Dropout(0.25),

Dense(output_dim=hidden3_num_units, input_dim=hidden2_num_units, activation='relu'),

Dropout(0.25),

Dense(output_dim=hidden4_num_units, input_dim=hidden3_num_units, activation='relu'),

Dropout(0.25),

Dense(output_dim=hidden5_num_units, input_dim=hidden4_num_units, activation='relu'),

Dropout(0.25),

Dense(output_dim=output_num_units, input_dim=hidden5_num_units, activation='softmax'),

])

model.compile(loss='categorical_crossentropy', optimizer='adam', metrics=['accuracy'])

trained_model_5d = model.fit(x_train, y_train, nb_epoch=epochs, batch_size=batch_size, validation_data=(x_test, y_test))

還可以,準確率比一開始提高了一些。

數據增強

from keras.preprocessing.image importImageDataGenerator

datagen = ImageDataGenerator(zca_whitening=True)

# 加載數據

train = pd.read_csv(os.path.join(data_dir, 'Train', 'train.csv'))

temp = []

for img_name in train.filename:

image_path = os.path.join(data_dir, 'Train', 'Images', 'train', img_name)

img = imread(image_path, flatten=True)

img = img.astype('float32')

temp.append(img)

x_train = np.stack(temp)

X_train = x_train.reshape(x_train.shape[0], 1, 28, 28)

X_train = X_train.astype('float32')

# 從數據中擬合參數——增加訓練數據

datagen.fit(X_train)

在這里,我們用了zca_whitening,它突出了每個數字的輪廓,如下圖所示:

## splitting

y_train = keras.utils.np_utils.to_categorical(train.label.values)

split_size = int(x_train.shape[0]*0.7)

x_train, x_test = X_train[:split_size], X_train[split_size:]

y_train, y_test = y_train[:split_size], y_train[split_size:]

## reshaping

x_train=np.reshape(x_train,(x_train.shape[0],-1))/255

x_test=np.reshape(x_test,(x_test.shape[0],-1))/255

## structure using dropout

from keras.layers.core importDropout

model = Sequential([

Dense(output_dim=hidden1_num_units, input_dim=input_num_units, activation='relu'),

Dropout(0.25),

Dense(output_dim=hidden2_num_units, input_dim=hidden1_num_units, activation='relu'),

Dropout(0.25),

Dense(output_dim=hidden3_num_units, input_dim=hidden2_num_units, activation='relu'),

Dropout(0.25),

Dense(output_dim=hidden4_num_units, input_dim=hidden3_num_units, activation='relu'),

Dropout(0.25),

Dense(output_dim=hidden5_num_units, input_dim=hidden4_num_units, activation='relu'),

Dropout(0.25),

Dense(output_dim=output_num_units, input_dim=hidden5_num_units, activation='softmax'),

])

model.compile(loss='categorical_crossentropy', optimizer='adam', metrics=['accuracy'])

trained_model_5d = model.fit(x_train, y_train, nb_epoch=epochs, batch_size=batch_size, validation_data=(x_test, y_test))

提升非常明顯!

早停法

from keras.callbacks importEarlyStopping

model.compile(loss='categorical_crossentropy', optimizer='adam', metrics=['accuracy'])

trained_model_5d = model.fit(x_train, y_train, nb_epoch=epochs, batch_size=batch_size, validation_data=(x_test, y_test)

, callbacks = [EarlyStopping(monitor='val_acc', patience=2)])

和上面那些方法相比,早停法只跑了5個epoch就停止了,因為預測準確率沒有提高。但是如果我們增加迭代的次數,它應該能給出更好的結果。

聲明:本文內容及配圖由入駐作者撰寫或者入駐合作網站授權轉載。文章觀點僅代表作者本人,不代表電子發燒友網立場。文章及其配圖僅供工程師學習之用,如有內容侵權或者其他違規問題,請聯系本站處理。 舉報投訴
  • 神經網絡
    +關注

    關注

    42

    文章

    4765

    瀏覽量

    100566
  • 正則化
    +關注

    關注

    0

    文章

    17

    瀏覽量

    8123
  • python
    +關注

    關注

    56

    文章

    4783

    瀏覽量

    84473

原文標題:一文概述深度學習中的正則化(含Python代碼)

文章出處:【微信號:jqr_AI,微信公眾號:論智】歡迎添加關注!文章轉載請注明出處。

收藏 人收藏

    評論

    相關推薦

    神經網絡中避免擬合5種方法介紹

    丟棄法是一種避免神經網絡擬合正則技術。像L1和L2這樣的正則技術通過修改代價函數來減少
    發表于 02-04 11:30 ?2.5w次閱讀
    神經網絡中避免<b class='flag-5'>過</b><b class='flag-5'>擬合</b>5種<b class='flag-5'>方法</b>介紹

    深層神經網絡模型的訓練:擬合優化

    為了訓練出高效可用的深層神經網絡模型,在訓練時必須要避免擬合的現象。擬合現象的優化方法通常有三種。
    的頭像 發表于 12-02 14:17 ?2698次閱讀
    深層神經網絡模型的訓練:<b class='flag-5'>過</b><b class='flag-5'>擬合</b>優化

    機器學習基礎知識 包括評估問題,理解擬合、欠擬合以及解決問題的技巧

    學習通用的,一部分用于解決擬合問題的技術(如dropout)除外。 4.1 三類機器學習問題 在之前的所有例子中,嘗試解決的是分類(預測貓或狗)或回歸(預測用戶在平臺上花費的平均時間)問題。所有這些都是有監督學習的例子,目的是
    發表于 07-12 09:28 ?922次閱讀
    機器學習基礎知識 包括評估問題,理解<b class='flag-5'>過</b><b class='flag-5'>擬合</b>、欠<b class='flag-5'>擬合</b>以及解決問題的技巧

    采集正弦曲線零點附近有波動,怎么曲線擬合

    采集正弦曲線,得到了一組數,零點附近有波動,怎么曲線擬合,將其擬合成標準的正弦曲線的點?
    發表于 04-09 15:13

    擬合,欠擬合以及模型的判斷

    python-學習曲線,判斷過擬合,欠擬合
    發表于 04-24 10:23

    模型的擬合之欠擬合總體解決方案

    15 模型的擬合 & 欠擬合 & 總體解決方案
    發表于 05-15 07:49

    深度學習中擬合/欠擬合的問題及解決方案

    的數據可以對未來的數據進行推測與模擬,因此都是使用歷史數據建立模型,即使用已經產生的數據去訓練,然后使用該模型去擬合未來的數據。 在我們機器學習和深度學習的訓練過程中,經常會出現擬合和欠擬合
    發表于 01-28 06:57

    曲線擬合的判定方法有哪幾種

    曲線擬合是什么意思?曲線擬合的判定方法有哪幾種呢?
    發表于 11-19 06:48

    基于擬合神經網絡的混沌偽隨機序列

    偽隨機序列在保密通信、擴頻通信、密碼學等領域具有重要作用。本文結合神經網絡和混沌映射的特點,提出了一種基于擬合BP 神經網絡的混沌偽隨機序列產生方法。以logist
    發表于 12-22 14:12 ?6次下載

    【連載】深度學習筆記4:深度神經網絡的正則

    今天要寫的是關于機器學習和深度學習中的一項關鍵技術:正則。相信在機器學習領域摸爬滾打多年的你一定知道正則是防止模型
    的頭像 發表于 08-14 11:58 ?3319次閱讀

    擬合擬合是什么?解決方法總結

    擬合是指模型在訓練集上表現很好,到了驗證和測試階段就大不如意了,即模型的泛能力很差。
    的頭像 發表于 01-29 17:48 ?3.1w次閱讀
    欠<b class='flag-5'>擬合</b>和<b class='flag-5'>過</b><b class='flag-5'>擬合</b>是什么?解決<b class='flag-5'>方法</b>總結

    深度學習中擬合、欠擬合問題及解決方案

    如何判斷過擬合呢?我們在訓練過程中會定義訓練誤差,驗證集誤差,測試集誤差(泛誤差)。訓練誤差總是減少的,而泛誤差一開始會減少,但到一定程序后不減反而增加,這時候便出現了
    發表于 01-22 07:44 ?6次下載
    深度學習中<b class='flag-5'>過</b><b class='flag-5'>擬合</b>、欠<b class='flag-5'>擬合</b>問題及解決方案

    正則方法DropKey: 兩行代碼高效緩解視覺Transformer擬合

    美圖影像研究院(MT Lab)與中國科學院大學在 CVPR 2023 上發表了一篇文章,提出一種新穎且即插即用的正則器 DropKey,該正則器可以有效緩解 Vision Tran
    的頭像 發表于 04-17 11:35 ?1148次閱讀

    擬合、泛和偏差-方差權衡

    在機器學習中,過度擬合是當模型變得過于復雜并開始過于接近訓練數據時發生的常見問題。這意味著該模型可能無法很好地推廣到新的、看不見的數據,因為它基本上記住了訓練數據,而不是真正學習底層模式或關系。技術術語來說,考慮一個回歸模型,它需要線性關系,而是使用多項式表示。
    發表于 06-12 09:31 ?486次閱讀
    <b class='flag-5'>過</b><b class='flag-5'>擬合</b>、泛<b class='flag-5'>化</b>和偏差-方差權衡

    深度學習模型中的擬合正則

    測試數據或新數據上表現不佳的現象。為了解決這個問題,正則(Regularization)技術應運而生,成為深度學習中不可或缺的一部分。本文將從擬合的原因、表現、
    的頭像 發表于 07-09 15:56 ?806次閱讀