A. 《python神經網路》2——神經元
雖然計算機擁有相對大量的電子計算元件、巨大的存儲空間,並且這些計算機的運行頻率比肉蓬蓬、軟綿綿的生物大腦要快得多,但是即使是像鴿子一樣小的大腦,其能力也遠遠大於這些電子計算機。
傳統的計算機按照嚴格的串列順序,相當准確具體地處理數據。對於這些冰冷堅硬的計算機而言,不存在模糊性和不確定性。而另一方面,動物的大腦表面上看起來以慢得多的節奏運行,卻似乎以並行方式處理信號,模糊性是其計算的一種特徵。
雖然神經元有各種形式,但是所有的神經元都是將電信號從一端傳輸到另一端,沿著軸突,將電信號從樹突傳到樹突。然後,這些信號從 一個神經元傳遞到另一個神經元。
我們需要多少神經元才能執行相對復雜的有趣任務呢?
一般來說,能力非常強的人類大腦有大約1000億個神經元!一隻果蠅有約10萬個神經元,能夠飛翔、覓食、躲避危險、尋找食物以及執行許多相當復雜的任務。 10萬個神經元,這個數字恰好落在了現代計算機試圖復制的范圍內。 一隻線蟲僅僅具有302個神經元,與今天的數字計算資源相比,簡直就是微乎其微!但是一直線蟲能夠完成一些相當有用的任務,而這些任務對於尺寸大得多的傳統計算機程序而言卻難以完成。
激活函數:
階躍函數,S函數。
B. 深度學習 python怎麼入門 知乎
自學深度學習是一個漫長而艱巨的過程。您需要有很強的線性代數和微積分背景,良好的Python編程技能,並扎實掌握數據科學、機器學習和數據工程。即便如此,在你開始將深度學習應用於現實世界的問題,並有可能找到一份深度學習工程師的工作之前,你可能需要一年多的學習和實踐。然而,知道從哪裡開始,對軟化學習曲線有很大幫助。如果我必須重新學習Python的深度學習,我會從Andrew Trask寫的Grokking deep learning開始。大多數關於深度學習的書籍都要求具備機器學習概念和演算法的基本知識。除了基本的數學和編程技能之外,Trask的書不需要任何先決條件就能教你深度學習的基礎知識。這本書不會讓你成為一個深度學習的向導(它也沒有做這樣的聲明),但它會讓你走上一條道路,讓你更容易從更高級的書和課程中學習。用Python構建人工神經元
大多數深度學習書籍都是基於一些流行的Python庫,如TensorFlow、PyTorch或Keras。相比之下,《運用深度學習》(Grokking Deep Learning)通過從零開始、一行一行地構建內容來教你進行深度學習。
《運用深度學習》
你首先要開發一個人工神經元,這是深度學習的最基本元素。查斯克將帶領您了解線性變換的基本知識,這是由人工神經元完成的主要計算。然後用普通的Python代碼實現人工神經元,無需使用任何特殊的庫。
這不是進行深度學習的最有效方式,因為Python有許多庫,它們利用計算機的圖形卡和CPU的並行處理能力來加速計算。但是用普通的Python編寫一切對於學習深度學習的來龍去是非常好的。
在Grokking深度學習中,你的第一個人工神經元只接受一個輸入,將其乘以一個隨機權重,然後做出預測。然後測量預測誤差,並應用梯度下降法在正確的方向上調整神經元的權重。有了單個神經元、單個輸入和單個輸出,理解和實現這個概念變得非常容易。您將逐漸增加模型的復雜性,使用多個輸入維度、預測多個輸出、應用批處理學習、調整學習速率等等。
您將通過逐步添加和修改前面章節中編寫的Python代碼來實現每個新概念,逐步創建用於進行預測、計算錯誤、應用糾正等的函數列表。當您從標量計算轉移到向量計算時,您將從普通的Python操作轉移到Numpy,這是一個特別擅長並行計算的庫,在機器學習和深度學習社區中非常流行。
Python的深度神經網路
有了這些人造神經元的基本構造塊,你就可以開始創建深層神經網路,這基本上就是你將幾層人造神經元疊放在一起時得到的結果。
當您創建深度神經網路時,您將了解激活函數,並應用它們打破堆疊層的線性並創建分類輸出。同樣,您將在Numpy函數的幫助下自己實現所有功能。您還將學習計算梯度和傳播錯誤通過層傳播校正跨不同的神經元。
隨著您越來越熟悉深度學習的基礎知識,您將學習並實現更高級的概念。這本書的特點是一些流行的正規化技術,如早期停止和退出。您還將獲得自己版本的卷積神經網路(CNN)和循環神經網路(RNN)。
在本書結束時,您將把所有內容打包到一個完整的Python深度學習庫中,創建自己的層次結構類、激活函數和神經網路體系結構(在這一部分,您將需要面向對象的編程技能)。如果您已經使用過Keras和PyTorch等其他Python庫,那麼您會發現最終的體系結構非常熟悉。如果您沒有,您將在將來更容易地適應這些庫。
在整本書中,查斯克提醒你熟能生巧;他鼓勵你用心編寫自己的神經網路,而不是復制粘貼任何東西。
代碼庫有點麻煩
並不是所有關於Grokking深度學習的東西都是完美的。在之前的一篇文章中,我說過定義一本好書的主要內容之一就是代碼庫。在這方面,查斯克本可以做得更好。
在GitHub的Grokking深度學習庫中,每一章都有豐富的jupiter Notebook文件。jupiter Notebook是一個學習Python機器學習和深度學習的優秀工具。然而,jupiter的優勢在於將代碼分解為幾個可以獨立執行和測試的小單元。Grokking深度學習的一些筆記本是由非常大的單元格組成的,其中包含大量未注釋的代碼。
這在後面的章節中會變得尤其困難,因為代碼會變得更長更復雜,在筆記本中尋找自己的方法會變得非常乏味。作為一個原則問題,教育材料的代碼應該被分解成小單元格,並在關鍵區域包含注釋。
此外,Trask在Python 2.7中編寫了這些代碼。雖然他已經確保了代碼在Python 3中也能順暢地工作,但它包含了已經被Python開發人員棄用的舊編碼技術(例如使用「for i in range(len(array))」範式在數組上迭代)。
更廣闊的人工智慧圖景
Trask已經完成了一項偉大的工作,它匯集了一本書,既可以為初學者,也可以為有經驗的Python深度學習開發人員填補他們的知識空白。
但正如泰溫·蘭尼斯特(Tywin Lannister)所說(每個工程師都會同意),「每個任務都有一個工具,每個工具都有一個任務。」深度學習並不是一根可以解決所有人工智慧問題的魔杖。事實上,對於許多問題,更簡單的機器學習演算法,如線性回歸和決策樹,將表現得和深度學習一樣好,而對於其他問題,基於規則的技術,如正則表達式和幾個if-else子句,將優於兩者。
關鍵是,你需要一整套工具和技術來解決AI問題。希望Grokking深度學習能夠幫助你開始獲取這些工具。
你要去哪裡?我當然建議選擇一本關於Python深度學習的深度書籍,比如PyTorch的深度學習或Python的深度學習。你還應該加深你對其他機器學習演算法和技術的了解。我最喜歡的兩本書是《動手機器學習》和《Python機器學習》。
你也可以通過瀏覽機器學習和深度學習論壇,如r/MachineLearning和r/deeplearning subreddits,人工智慧和深度學習Facebook組,或通過在Twitter上關注人工智慧研究人員來獲取大量知識。
AI的世界是巨大的,並且在快速擴張,還有很多東西需要學習。如果這是你關於深度學習的第一本書,那麼這是一個神奇旅程的開始。
C. 如何通過Python進行深度學習
作者 | Vihar Kurama
編譯 | 荷葉
來源 | 雲棲社區
摘要:深度學習背後的主要原因是人工智慧應該從人腦中汲取靈感。本文就用一個小例子無死角的介紹一下深度學習!
人腦模擬
深度學習背後的主要原因是人工智慧應該從人腦中汲取靈感。此觀點引出了「神經網路」這一術語。人腦中包含數十億個神經元,它們之間有數萬個連接。很多情況下,深度學習演算法和人腦相似,因為人腦和深度學習模型都擁有大量的編譯單元(神經元),這些編譯單元(神經元)在獨立的情況下都不太智能,但是當他們相互作用時就會變得智能。
我認為人們需要了解到深度學習正在使得很多幕後的事物變得更好。深度學習已經應用於谷歌搜索和圖像搜索,你可以通過它搜索像「擁抱」這樣的詞語以獲得相應的圖像。-傑弗里·辛頓
神經元
神經網路的基本構建模塊是人工神經元,它模仿了人類大腦的神經元。這些神經元是簡單、強大的計算單元,擁有加權輸入信號並且使用激活函數產生輸出信號。這些神經元分布在神經網路的幾個層中。
inputs 輸入 outputs 輸出 weights 權值 activation 激活
人工神經網路的工作原理是什麼?
深度學習由人工神經網路構成,該網路模擬了人腦中類似的網路。當數據穿過這個人工網路時,每一層都會處理這個數據的一方面,過濾掉異常值,辨認出熟悉的實體,並產生最終輸出。
輸入層:該層由神經元組成,這些神經元只接收輸入信息並將它傳遞到其他層。輸入層的圖層數應等於數據集里的屬性或要素的數量。輸出層:輸出層具有預測性,其主要取決於你所構建的模型類型。隱含層:隱含層處於輸入層和輸出層之間,以模型類型為基礎。隱含層包含大量的神經元。處於隱含層的神經元會先轉化輸入信息,再將它們傳遞出去。隨著網路受訓練,權重得到更新,從而使其更具前瞻性。
神經元的權重
權重是指兩個神經元之間的連接的強度或幅度。你如果熟悉線性回歸的話,可以將輸入的權重類比為我們在回歸方程中用的系數。權重通常被初始化為小的隨機數值,比如數值0-1。
前饋深度網路
前饋監督神經網路曾是第一個也是最成功的學習演算法。該網路也可被稱為深度網路、多層感知機(MLP)或簡單神經網路,並且闡明了具有單一隱含層的原始架構。每個神經元通過某個權重和另一個神經元相關聯。
該網路處理向前處理輸入信息,激活神經元,最終產生輸出值。在此網路中,這稱為前向傳遞。
inputlayer 輸入層 hidden layer 輸出層 output layer 輸出層
激活函數
激活函數就是求和加權的輸入到神經元的輸出的映射。之所以稱之為激活函數或傳遞函數是因為它控制著激活神經元的初始值和輸出信號的強度。
用數學表示為:
我們有許多激活函數,其中使用最多的是整流線性單元函數、雙曲正切函數和solfPlus函數。
激活函數的速查表如下:
反向傳播
在網路中,我們將預測值與預期輸出值相比較,並使用函數計算其誤差。然後,這個誤差會傳回這個網路,每次傳回一個層,權重也會根絕其導致的誤差值進行更新。這個聰明的數學法是反向傳播演算法。這個步驟會在訓練數據的所有樣本中反復進行,整個訓練數據集的網路更新一輪稱為一個時期。一個網路可受訓練數十、數百或數千個時期。
prediction error 預測誤差
代價函數和梯度下降
代價函數度量了神經網路對給定的訓練輸入和預期輸出「有多好」。該函數可能取決於權重、偏差等屬性。
代價函數是單值的,並不是一個向量,因為它從整體上評估神經網路的性能。在運用梯度下降最優演算法時,權重在每個時期後都會得到增量式地更新。
兼容代價函數
用數學表述為差值平方和:
target 目標值 output 輸出值
權重更新的大小和方向是由在代價梯度的反向上採取步驟計算出的。
其中η 是學習率
其中Δw是包含每個權重系數w的權重更新的向量,其計算方式如下:
target 目標值 output 輸出值
圖表中會考慮到單系數的代價函數
initial weight 初始權重 gradient 梯度 global cost minimum 代價極小值
在導數達到最小誤差值之前,我們會一直計算梯度下降,並且每個步驟都會取決於斜率(梯度)的陡度。
多層感知器(前向傳播)
這類網路由多層神經元組成,通常這些神經元以前饋方式(向前傳播)相互連接。一層中的每個神經元可以直接連接後續層的神經元。在許多應用中,這些網路的單元會採用S型函數或整流線性單元(整流線性激活)函數作為激活函數。
現在想想看要找出處理次數這個問題,給定的賬戶和家庭成員作為輸入
要解決這個問題,首先,我們需要先創建一個前向傳播神經網路。我們的輸入層將是家庭成員和賬戶的數量,隱含層數為1, 輸出層將是處理次數。
將圖中輸入層到輸出層的給定權重作為輸入:家庭成員數為2、賬戶數為3。
現在將通過以下步驟使用前向傳播來計算隱含層(i,j)和輸出層(k)的值。
步驟:
1, 乘法-添加方法。
2, 點積(輸入*權重)。
3,一次一個數據點的前向傳播。
4, 輸出是該數據點的預測。
i的值將從相連接的神經元所對應的輸入值和權重中計算出來。
i = (2 * 1) + (3* 1) → i = 5
同樣地,j = (2 * -1) + (3 * 1) → j =1
K = (5 * 2) + (1* -1) → k = 9
Python中的多層感知器問題的解決
激活函數的使用
為了使神經網路達到其最大預測能力,我們需要在隱含層應用一個激活函數,以捕捉非線性。我們通過將值代入方程式的方式來在輸入層和輸出層應用激活函數。
這里我們使用整流線性激活(ReLU):
用Keras開發第一個神經網路
關於Keras:
Keras是一個高級神經網路的應用程序編程介面,由Python編寫,能夠搭建在TensorFlow,CNTK,或Theano上。
使用PIP在設備上安裝Keras,並且運行下列指令。
在keras執行深度學習程序的步驟
1,載入數據;
2,創建模型;
3,編譯模型;
4,擬合模型;
5,評估模型。
開發Keras模型
全連接層用Dense表示。我們可以指定層中神經元的數量作為第一參數,指定初始化方法為第二參數,即初始化參數,並且用激活參數確定激活函數。既然模型已經創建,我們就可以編譯它。我們在底層庫(也稱為後端)用高效數字型檔編譯模型,底層庫可以用Theano或TensorFlow。目前為止,我們已經完成了創建模型和編譯模型,為進行有效計算做好了准備。現在可以在PIMA數據上運行模型了。我們可以在模型上調用擬合函數f(),以在數據上訓練或擬合模型。
我們先從KERAS中的程序開始,
神經網路一直訓練到150個時期,並返回精確值。
D. 請大神幫幫忙,python神經網路代碼運行出錯,程序找不到訓練集,請問如何讓程序找到MNIST訓練集的位置
學習人工智慧時,我給自己定了一個目標--用Python寫一個簡單的神經網路。為了確保真得理解它,我要求自己不使用任何神經網路庫,從頭寫起。多虧了Andrew Trask寫得一篇精彩的博客,我做到了!下面貼出那九行代碼:
在這篇文章中,我將解釋我是如何做得,以便你可以寫出你自己的。我將會提供一個長點的但是更完美的源代碼。
首先,神經網路是什麼?人腦由幾千億由突觸相互連接的細胞(神經元)組成。突觸傳入足夠的興奮就會引起神經元的興奮。這個過程被稱為「思考」。
我們可以在計算機上寫一個神經網路來模擬這個過程。不需要在生物分子水平模擬人腦,只需模擬更高層級的規則。我們使用矩陣(二維數據表格)這一數學工具,並且為了簡單明了,只模擬一個有3個輸入和一個輸出的神經元。
我們將訓練神經元解決下面的問題。前四個例子被稱作訓練集。你發現規律了嗎?『?』是0還是1?
你可能發現了,輸出總是等於輸入中最左列的值。所以『?』應該是1。
訓練過程
但是如何使我們的神經元回答正確呢?賦予每個輸入一個權重,可以是一個正的或負的數字。擁有較大正(或負)權重的輸入將決定神經元的輸出。首先設置每個權重的初始值為一個隨機數字,然後開始訓練過程:
取一個訓練樣本的輸入,使用權重調整它們,通過一個特殊的公式計算神經元的輸出。
計算誤差,即神經元的輸出與訓練樣本中的期待輸出之間的差值。
根據誤差略微地調整權重。
重復這個過程1萬次。
最終權重將會變為符合訓練集的一個最優解。如果使用神經元考慮這種規律的一個新情形,它將會給出一個很棒的預測。
這個過程就是back propagation。
計算神經元輸出的公式
你可能會想,計算神經元輸出的公式是什麼?首先,計算神經元輸入的加權和,即
接著使之規范化,結果在0,1之間。為此使用一個數學函數--Sigmoid函數:
Sigmoid函數的圖形是一條「S」狀的曲線。
把第一個方程代入第二個,計算神經元輸出的最終公式為:
你可能注意到了,為了簡單,我們沒有引入最低興奮閾值。
調整權重的公式
我們在訓練時不斷調整權重。但是怎麼調整呢?可以使用「Error Weighted Derivative」公式:
為什麼使用這個公式?首先,我們想使調整和誤差的大小成比例。其次,乘以輸入(0或1),如果輸入是0,權重就不會調整。最後,乘以Sigmoid曲線的斜率(圖4)。為了理解最後一條,考慮這些:
我們使用Sigmoid曲線計算神經元的輸出
如果輸出是一個大的正(或負)數,這意味著神經元採用這種(或另一種)方式
從圖四可以看出,在較大數值處,Sigmoid曲線斜率小
如果神經元認為當前權重是正確的,就不會對它進行很大調整。乘以Sigmoid曲線斜率便可以實現這一點
Sigmoid曲線的斜率可以通過求導得到:
把第二個等式代入第一個等式里,得到調整權重的最終公式:
當然有其他公式,它們可以使神經元學習得更快,但是這個公式的優點是非常簡單。
構造Python代碼
雖然我們沒有使用神經網路庫,但是將導入Python數學庫numpy里的4個方法。分別是:
exp--自然指數
array--創建矩陣
dot--進行矩陣乘法
random--產生隨機數
比如, 我們可以使用array()方法表示前面展示的訓練集:
「.T」方法用於矩陣轉置(行變列)。所以,計算機這樣存儲數字:
我覺得我們可以開始構建更優美的源代碼了。給出這個源代碼後,我會做一個總結。
我對每一行源代碼都添加了注釋來解釋所有內容。注意在每次迭代時,我們同時處理所有訓練集數據。所以變數都是矩陣(二維數據表格)。下面是一個用Python寫地完整的示例代碼。
結語
試著在命令行運行神經網路:
你應該看到這樣的結果:
我們做到了!我們用Python構建了一個簡單的神經網路!
首先神經網路對自己賦予隨機權重,然後使用訓練集訓練自己。接著,它考慮一種新的情形[1, 0, 0]並且預測了0.99993704。正確答案是1。非常接近!
傳統計算機程序通常不會學習。而神經網路卻能自己學習,適應並對新情形做出反應,這是多麼神奇,就像人類一樣。
E. Hopfield神經網路用python實現講解
神經網路結構具有以下三個特點:
神經元之間全連接,並且為單層神經網路。
每個神經元既是輸入又是輸出,導致得到的權重矩陣相對稱,故可節約計算量。
在輸入的激勵下,其輸出會產生不斷的狀態變化,這個反饋過程會一直反復進行。假如Hopfield神經網路是一個收斂的穩定網路,則這個反饋與迭代的計算過程所產生的變化越來越小,一旦達到了穩定的平衡狀態,Hopfield網路就會輸出一個穩定的恆值。
Hopfield網路可以儲存一組平衡點,使得當給定網路一組初始狀態時,網路通過自行運行而最終收斂於這個設計的平衡點上。當然,根據熱力學上,平衡狀態分為stable state和metastable state, 這兩種狀態在網路的收斂過程中都是非常可能的。
為遞歸型網路,t時刻的狀態與t-1時刻的輸出狀態有關。之後的神經元更新過程也採用的是非同步更新法(Asynchronous)。
Hopfield神經網路用python實現
F. BP神經網路——Python簡單實現三層神經網路(Numpy)
我們將在Python中創建一個NeuralNetwork類,以訓練神經元以給出准確的預測。該課程還將具有其他幫助程序功能。
1. 應用Sigmoid函數
我們將使用 Sigmoid函數 (它繪制一條「 S」形曲線)作為神經網路的激活函數。
2. 訓練模型
這是我們將教神經網路做出准確預測的階段。每個輸入將具有權重(正或負)。
這意味著具有大量正權重或大量負權重的輸入將對結果輸出產生更大的影響。
我們最初是將每個權重分配給一個隨機數。
本文參考翻譯於此網站 —— 原文
G. 利用Python實現卷積神經網路的可視化
在本文中,將探討如何可視化卷積神經網路(CNN),該網路在計算機視覺中使用最為廣泛。首先了解CNN模型可視化的重要性,其次介紹可視化的幾種方法,同時以一個用例幫助讀者更好地理解模型可視化這一概念。
正如上文中介紹的癌症腫瘤診斷案例所看到的,研究人員需要對所設計模型的工作原理及其功能掌握清楚,這點至關重要。一般而言,一名深度學習研究者應該記住以下幾點:
1.1 理解模型是如何工作的
1.2 調整模型的參數
1.3 找出模型失敗的原因
1.4 向消費者/終端用戶或業務主管解釋模型做出的決定
2.可視化CNN模型的方法
根據其內部的工作原理,大體上可以將CNN可視化方法分為以下三類:
初步方法:一種顯示訓練模型整體結構的簡單方法
基於激活的方法:對單個或一組神經元的激活狀態進行破譯以了解其工作過程
基於梯度的方法:在訓練過程中操作前向傳播和後向傳播形成的梯度
下面將具體介紹以上三種方法,所舉例子是使用Keras深度學習庫實現,另外本文使用的數據集是由「識別數字」競賽提供。因此,讀者想復現文中案例時,請確保安裝好Kears以及執行了這些步驟。
研究者能做的最簡單的事情就是繪制出模型結構圖,此外還可以標注神經網路中每層的形狀及參數。在keras中,可以使用如下命令完成模型結構圖的繪制:
model.summary()_________________________________________________________________Layer (type) Output Shape Param #
=================================================================conv2d_1 (Conv2D) (None, 26, 26, 32) 320_________________________________________________________________conv2d_2 (Conv2D) (None, 24, 24, 64) 18496_________________________________________________________________max_pooling2d_1 (MaxPooling2 (None, 12, 12, 64) 0_________________________________________________________________dropout_1 (Dropout) (None, 12, 12, 64) 0_________________________________________________________________flatten_1 (Flatten) (None, 9216) 0_________________________________________________________________dense_1 (Dense) (None, 128) 1179776_________________________________________________________________dropout_2 (Dropout) (None, 128) 0_________________________________________________________________preds (Dense) (None, 10) 1290
=================================================================Total params: 1,199,882Trainable params: 1,199,882Non-trainable params: 0
還可以用一個更富有創造力和表現力的方式呈現模型結構框圖,可以使用keras.utils.vis_utils函數完成模型體系結構圖的繪制。
另一種方法是繪制訓練模型的過濾器,這樣就可以了解這些過濾器的表現形式。例如,第一層的第一個過濾器看起來像:
top_layer = model.layers[0]plt.imshow(top_layer.get_weights()[0][:, :, :, 0].squeeze(), cmap='gray')
一般來說,神經網路的底層主要是作為邊緣檢測器,當層數變深時,過濾器能夠捕捉更加抽象的概念,比如人臉等。
為了理解神經網路的工作過程,可以在輸入圖像上應用過濾器,然後繪制其卷積後的輸出,這使得我們能夠理解一個過濾器其特定的激活模式是什麼。比如,下圖是一個人臉過濾器,當輸入圖像是人臉圖像時候,它就會被激活。
from vis.visualization import visualize_activation
from vis.utils import utils
from keras import activations
from matplotlib import pyplot as plt
%matplotlib inline
plt.rcParams['figure.figsize'] = (18, 6)
# Utility to search for layer index by name.
# Alternatively we can specify this as -1 since it corresponds to the last layer.
layer_idx = utils.find_layer_idx(model, 'preds')
# Swap softmax with linear
model.layers[layer_idx].activation = activations.linear
model = utils.apply_modifications(model)
# This is the output node we want to maximize.filter_idx = 0
img = visualize_activation(model, layer_idx, filter_indices=filter_idx)
plt.imshow(img[..., 0])
同理,可以將這個想法應用於所有的類別,並檢查它們的模式會是什麼樣子。
for output_idx in np.arange(10):
# Lets turn off verbose output this time to avoid clutter and just see the output.
img = visualize_activation(model, layer_idx, filter_indices=output_idx, input_range=(0., 1.))
plt.figure()
plt.title('Networks perception of {}'.format(output_idx))
plt.imshow(img[..., 0])
在圖像分類問題中,可能會遇到目標物體被遮擋,有時候只有物體的一小部分可見的情況。基於圖像遮擋的方法是通過一個灰色正方形系統地輸入圖像的不同部分並監視分類器的輸出。這些例子清楚地表明模型在場景中定位對象時,若對象被遮擋,其分類正確的概率顯著降低。
為了理解這一概念,可以從數據集中隨機抽取圖像,並嘗試繪制該圖的熱圖(heatmap)。這使得我們直觀地了解圖像的哪些部分對於該模型而言的重要性,以便對實際類別進行明確的區分。
def iter_occlusion(image, size=8):
# taken from https://www.kaggle.com/blargl/simple-occlusion-and-saliency-maps
occlusion = np.full((size * 5, size * 5, 1), [0.5], np.float32)
occlusion_center = np.full((size, size, 1), [0.5], np.float32)
occlusion_padding = size * 2
# print('padding...')
image_padded = np.pad(image, ( \ (occlusion_padding, occlusion_padding), (occlusion_padding, occlusion_padding), (0, 0) \ ), 'constant', constant_values = 0.0)
for y in range(occlusion_padding, image.shape[0] + occlusion_padding, size):
for x in range(occlusion_padding, image.shape[1] + occlusion_padding, size):
tmp = image_padded.()
tmp[y - occlusion_padding:y + occlusion_center.shape[0] + occlusion_padding, \
x - occlusion_padding:x + occlusion_center.shape[1] + occlusion_padding] \ = occlusion
tmp[y:y + occlusion_center.shape[0], x:x + occlusion_center.shape[1]] = occlusion_center yield x - occlusion_padding, y - occlusion_padding, \
tmp[occlusion_padding:tmp.shape[0] - occlusion_padding, occlusion_padding:tmp.shape[1] - occlusion_padding]i = 23 # for exampledata = val_x[i]correct_class = np.argmax(val_y[i])
# input tensor for model.predictinp = data.reshape(1, 28, 28, 1)# image data for matplotlib's imshowimg = data.reshape(28, 28)
# occlusionimg_size = img.shape[0]
occlusion_size = 4print('occluding...')heatmap = np.zeros((img_size, img_size), np.float32)class_pixels = np.zeros((img_size, img_size), np.int16)
from collections import defaultdict
counters = defaultdict(int)for n, (x, y, img_float) in enumerate(iter_occlusion(data, size=occlusion_size)):
X = img_float.reshape(1, 28, 28, 1)
out = model.predict(X)
#print('#{}: {} @ {} (correct class: {})'.format(n, np.argmax(out), np.amax(out), out[0][correct_class]))
#print('x {} - {} | y {} - {}'.format(x, x + occlusion_size, y, y + occlusion_size))
heatmap[y:y + occlusion_size, x:x + occlusion_size] = out[0][correct_class]
class_pixels[y:y + occlusion_size, x:x + occlusion_size] = np.argmax(out)
counters[np.argmax(out)] += 1
正如之前的坦克案例中看到的那樣,怎麼才能知道模型側重於哪部分的預測呢?為此,可以使用顯著圖解決這個問題。顯著圖首先在這篇文章中被介紹。
使用顯著圖的概念相當直接——計算輸出類別相對於輸入圖像的梯度。這應該告訴我們輸出類別值對於輸入圖像像素中的微小變化是怎樣變化的。梯度中的所有正值告訴我們,像素的一個小變化會增加輸出值。因此,將這些梯度可視化可以提供一些直觀的信息,這種方法突出了對輸出貢獻最大的顯著圖像區域。
class_idx = 0indices = np.where(val_y[:, class_idx] == 1.)[0]
# pick some random input from here.idx = indices[0]
# Lets sanity check the picked image.from matplotlib import pyplot as plt%matplotlib inline
plt.rcParams['figure.figsize'] = (18, 6)plt.imshow(val_x[idx][..., 0])
from vis.visualization import visualize_saliency
from vis.utils import utilsfrom keras import activations# Utility to search for layer index by name.
# Alternatively we can specify this as -1 since it corresponds to the last layer.
layer_idx = utils.find_layer_idx(model, 'preds')
# Swap softmax with linearmodel.layers[layer_idx].activation = activations.linear
model = utils.apply_modifications(model)grads = visualize_saliency(model, layer_idx, filter_indices=class_idx, seed_input=val_x[idx])
# Plot with 'jet' colormap to visualize as a heatmap.plt.imshow(grads, cmap='jet')
# This corresponds to the Dense linear layer.for class_idx in np.arange(10):
indices = np.where(val_y[:, class_idx] == 1.)[0]
idx = indices[0]
f, ax = plt.subplots(1, 4)
ax[0].imshow(val_x[idx][..., 0])
for i, modifier in enumerate([None, 'guided', 'relu']):
grads = visualize_saliency(model, layer_idx, filter_indices=class_idx,
seed_input=val_x[idx], backprop_modifier=modifier)
if modifier is None:
modifier = 'vanilla'
ax[i+1].set_title(modifier)
ax[i+1].imshow(grads, cmap='jet')
類別激活映射(CAM)或grad-CAM是另外一種可視化模型的方法,這種方法使用的不是梯度的輸出值,而是使用倒數第二個卷積層的輸出,這樣做是為了利用存儲在倒數第二層的空間信息。
from vis.visualization import visualize_cam
# This corresponds to the Dense linear layer.for class_idx in np.arange(10):
indices = np.where(val_y[:, class_idx] == 1.)[0]
idx = indices[0]f, ax = plt.subplots(1, 4)
ax[0].imshow(val_x[idx][..., 0])
for i, modifier in enumerate([None, 'guided', 'relu']):
grads = visualize_cam(model, layer_idx, filter_indices=class_idx,
seed_input=val_x[idx], backprop_modifier=modifier)
if modifier is None:
modifier = 'vanilla'
ax[i+1].set_title(modifier)
ax[i+1].imshow(grads, cmap='jet')
本文簡單說明了CNN模型可視化的重要性,以及介紹了一些可視化CNN網路模型的方法,希望對讀者有所幫助,使其能夠在後續深度學習應用中構建更好的模型。 免費視頻教程:www.mlxs.top
H. 怎樣用python構建一個卷積神經網路
用keras框架較為方便
首先安裝anaconda,然後腔升瞎通過pip安裝keras
I. 如何用python和scikit learn實現神經網路
1:神經網路演算法簡介
2:Backpropagation演算法詳細介紹
3:非線性轉化方程舉例
4:自己實現神經網路演算法NeuralNetwork
5:基於NeuralNetwork的XOR實例
6:基於NeuralNetwork的手寫數字識別實例
7:scikit-learn中BernoulliRBM使用實例
8:scikit-learn中的手寫數字識別實例
一:神經網路演算法簡介
1:背景
以人腦神經網路為啟發,歷史上出現過很多版本,但最著名的是backpropagation
2:多層向前神經網路(Multilayer Feed-Forward Neural Network)
J. 怎樣用python構建一個卷積神經網路
用keras框架較為方便
首先安裝anaconda,然後通過pip安裝keras