1
雷鋒網(wǎng) AI 科技評(píng)論按:顧名思義,「表示」(representation)就是指在網(wǎng)絡(luò)中對(duì)信息進(jìn)行編碼的方式。為了讓大家充分理解「表示」,本文作者嘗試構(gòu)建一個(gè)能同時(shí)完成圖像描述,相似詞、相似圖像搜索以及通過描述圖像描述搜索圖像四項(xiàng)任務(wù)的深度神經(jīng)網(wǎng)絡(luò),從實(shí)操中讓大家感受「表示」的奇妙世界。雷鋒網(wǎng) AI 科技評(píng)論編譯如下。
眾所周知,神經(jīng)網(wǎng)絡(luò)十分擅長(zhǎng)處理特定領(lǐng)域的任務(wù),但在處理多任務(wù)時(shí)結(jié)果并不是那么理想。這與人類大腦不同,人類大腦能夠在多樣化任務(wù)中使用相同的概念。例如,假如你從來沒聽說過「分形」(fractal),不妨看一下下面這張圖:
在看到一張分形圖像后,人類能夠處理多個(gè)與之相關(guān)的任務(wù):
在一組圖像中,區(qū)分出分形圖像和一只貓的圖像;
在一張紙上,粗略地畫出分形圖的樣子(它不會(huì)很完美,但也不會(huì)是隨意的涂鴉);
將類似分形的圖像與非分形圖像進(jìn)行分類(你會(huì)毫不猶豫地將圖像按最相似到最不相似的方式進(jìn)行分類);
閉上眼睛,想象一下分形圖像是什么樣子的(即使現(xiàn)在不給你一張現(xiàn)成的分形圖象,你也可以在看過它一次之后,就想象出它的樣子,是不是很棒!)
那么,你是如何完成這些任務(wù)的呢?你的大腦中是否有專門負(fù)責(zé)處理這些任務(wù)的神經(jīng)網(wǎng)絡(luò)?
現(xiàn)代神經(jīng)科學(xué)對(duì)此給出了答案:大腦中的信息是跨不同的部位進(jìn)行分享和交流的。大腦究竟怎樣完成這些任務(wù)只是研究的一個(gè)領(lǐng)域,而對(duì)于這種執(zhí)行多任務(wù)的能力是怎樣產(chǎn)生的,我們也有一些線索——答案可能就存在于如何在神經(jīng)網(wǎng)絡(luò)中存儲(chǔ)和解釋數(shù)據(jù)。
顧名思義,「表示」(representation)就是指在網(wǎng)絡(luò)中對(duì)信息進(jìn)行編碼的方式。當(dāng)一個(gè)單詞、一個(gè)句子或一幅圖像(或其他任何東西)被輸入到一個(gè)訓(xùn)練好的神經(jīng)網(wǎng)絡(luò)時(shí),隨著權(quán)重與輸入相乘并進(jìn)行激活操作時(shí),它就能在連續(xù)的層上實(shí)現(xiàn)轉(zhuǎn)換。最后,我們?cè)谳敵鰧又械玫揭淮當(dāng)?shù)字,我們將其解釋為類標(biāo)簽或股價(jià),或網(wǎng)絡(luò)為之訓(xùn)練的任何其他任務(wù)。
這種神奇的輸入->輸出轉(zhuǎn)換因連續(xù)層中發(fā)生的輸入轉(zhuǎn)換得以實(shí)現(xiàn)。輸入數(shù)據(jù)的這些轉(zhuǎn)換即稱為「表示」。它的一個(gè)重要思想是,每一層都讓下一層更容易地執(zhí)行任務(wù)。這個(gè)過程讓連續(xù)層的存在變得更容易,進(jìn)而也使得激活(特定層上輸入數(shù)據(jù)的轉(zhuǎn)換)變得有意義。
我所說的有意義是指什么呢?讓我們看下面的示例,其展示了圖像分類器中不同層的激活:
圖像分類網(wǎng)絡(luò)的作用是將像素空間中的圖像轉(zhuǎn)化為更高級(jí)的概念空間。例如,一張最初用 RGB 值表示的汽車圖像,首先在第一層用邊緣空間表示,然后在第二層被表示為圓圈和基本形狀空間,在倒數(shù)第二層則開始使用高級(jí)對(duì)象(如車輪、車門等)表示。
隨著表示(由于深度網(wǎng)絡(luò)的層次性而自動(dòng)出現(xiàn))日益豐富,圖像分類的任務(wù)也變得微不足道。最后一層要做的就是權(quán)衡車輪和車門的概念更像汽車以及耳朵、眼睛的概念更像人。
由于這些中間層存儲(chǔ)有意義的輸入數(shù)據(jù)編碼,所以可以對(duì)多個(gè)任務(wù)使用相同的信息。例如,你可以使用一個(gè)語(yǔ)言模型(一個(gè)經(jīng)過訓(xùn)練、用于預(yù)測(cè)下一個(gè)單詞的循環(huán)神經(jīng)網(wǎng)絡(luò)),并解釋某個(gè)特定神經(jīng)元的激活以預(yù)測(cè)句子的情緒。
(via Unsupervised Sentiment Neuron)
一個(gè)令人驚訝的事實(shí)是,情感神經(jīng)元是在無監(jiān)督的語(yǔ)言建模任務(wù)中自然出現(xiàn)的。(相關(guān)文章請(qǐng)參閱:https://rakeshchada.github.io/Sentiment-Neuron.html)。網(wǎng)絡(luò)經(jīng)過訓(xùn)練來預(yù)測(cè)下一個(gè)單詞,然而在任務(wù)中我們沒有要求網(wǎng)絡(luò)預(yù)測(cè)情緒。也許情感是一個(gè)非常有用的概念,以至于網(wǎng)絡(luò)為了更好地進(jìn)行語(yǔ)言建模而創(chuàng)造了它。
一旦你理解了「表示」這個(gè)概念,你就會(huì)開始從完全不同的角度來理解深層神經(jīng)網(wǎng)絡(luò)。你會(huì)開始將表示(sensing representations)視作一種能夠讓不同網(wǎng)絡(luò)(或同一網(wǎng)絡(luò)的不同部分)之間實(shí)現(xiàn)通信的可轉(zhuǎn)換的語(yǔ)言。
為了充分理解「表示」,讓我們來構(gòu)建一個(gè)能同時(shí)完成四個(gè)任務(wù)的的深度神經(jīng)網(wǎng)絡(luò):
圖像描述生成器:給定圖像,為其生成標(biāo)題
相似單詞生成器:給定一個(gè)單詞,查找與之相似的其他單詞
視覺相似的圖像搜索:給定一幅圖像,找出與之最相似的圖像
通過描述圖像描述搜索圖像:給出文本描述,搜索具有所描述的內(nèi)容的圖像
這三個(gè)任務(wù)中的每一個(gè)本身都是一個(gè)項(xiàng)目,一般來說需要三個(gè)模型。但我們現(xiàn)在要用一個(gè)模型來完成所有這些任務(wù)。
該代碼將采用 Pytorch 在 Jupyter Notebook 中編寫,大家可以前往這個(gè)存儲(chǔ)庫(kù)進(jìn)行下載:
在網(wǎng)上有很多實(shí)現(xiàn)圖像描述的好教程,所以這里就不深入講解。我的實(shí)現(xiàn)與這個(gè)教程中所使用的方法完全相同:構(gòu)建一個(gè)自動(dòng)化的圖像標(biāo)題應(yīng)用程序(教程鏈接:https://daniel.lasiman.com/post/image-captioning/)。關(guān)鍵的區(qū)別在于,我的實(shí)現(xiàn)是使用 Pytorch 實(shí)現(xiàn)的,而教程使用的是 Keras。
要繼續(xù)學(xué)習(xí),你需要下載 Flickr8K 數(shù)據(jù)集(1GB Flickr8K 數(shù)據(jù)集的下載鏈接:https://github.com/jbrownlee/Datasets/releases/download/Flickr8k/Flickr8k_Dataset.zip,不過我不確定這個(gè)鏈接的有效期多長(zhǎng))。填好這張表格(https://forms.illinois.edu/sec/1713398)后,你的電子郵件會(huì)收到一個(gè)下載鏈接。將 zip 文件解壓到與筆記本目錄相同的「Flicker8k_Dataset」文件夾中。您還需要從這里(http://cs.stanford.edu/people/karpathy/deepimagesent/caption_datasets.zip)下載描述,并提取「caption_datasets」文件夾中的描述。
圖像描述一般由兩個(gè)組成部分:
a)圖像編碼器(image encoder),它接收輸入圖像并以一種對(duì)圖像描述有意義的格式來表示圖像;
b)圖說解碼器(caption decoder),它接受圖像表示,并輸出文本描述。
圖像編碼器是一個(gè)深度卷積網(wǎng)絡(luò),而圖說解碼器則是傳統(tǒng)的 LSTM/GRU 循環(huán)神經(jīng)網(wǎng)絡(luò)。當(dāng)然,我們可以從頭開始訓(xùn)練它們。但這樣做的話,就需要比我們現(xiàn)有的(8k 張圖像)更多的數(shù)據(jù)和更長(zhǎng)的訓(xùn)練時(shí)間。因此,我們不從頭開始訓(xùn)練圖像編碼器,而是使用一個(gè)預(yù)訓(xùn)練的圖像分類器,并使用它倒數(shù)第二層的激活。
你將在本文中看到許多神奇的表示示例,下面這個(gè)示例是第一個(gè)。我使用在 ImageNet 上進(jìn)行了訓(xùn)練的 PyTorch modelzoo 中可用的 Inception 網(wǎng)絡(luò)來對(duì) 100 個(gè)類別的圖像進(jìn)行分類,并使用該網(wǎng)絡(luò)來提供一個(gè)可以輸入給循環(huán)神經(jīng)網(wǎng)絡(luò)中的表示。
via https://daniel.lasiman.com/post/image-captioning/
值得一提的是,雖然 Inception 網(wǎng)絡(luò)從未對(duì)圖說生成任務(wù)進(jìn)行過訓(xùn)練,但是它的確有效!
如我在通過機(jī)器學(xué)習(xí)形成機(jī)器學(xué)習(xí)思路一文中所做的那樣,我們使用了一個(gè)預(yù)訓(xùn)練的語(yǔ)言模型來作為圖說解碼器。但這一次,由于我重新實(shí)現(xiàn)了在教程中運(yùn)行良好的模型,僅按照教程的步驟便從頭開始訓(xùn)練了一個(gè)解碼器。
完整的模型架構(gòu)如下圖所示:
Image via https://daniel.lasiman.com/post/image-captioning/
你可以從頭開始訓(xùn)練模型,但是在 CPU 上就要花費(fèi)幾天時(shí)間(我沒有對(duì) GPU 進(jìn)行優(yōu)化)。但不用擔(dān)心,我的筆記本電腦度過了幾個(gè)不眠之夜訓(xùn)練出來的模型成果,可供大家使用。(如果你是從頭開始訓(xùn)練,需要注意的是,當(dāng)運(yùn)行的平均損失約為 2.8 時(shí),我在大概 40 epochs 時(shí)停止了訓(xùn)練。)
性能
我采用的集束搜索(beam search)方法實(shí)現(xiàn)了良好的性能。下面是網(wǎng)絡(luò)為測(cè)試集中的圖像所生成的圖說示例(網(wǎng)絡(luò)此前從未見過這種圖像)。
用我自己的照片試試,看看網(wǎng)絡(luò)生成的圖說是什么:
效果不錯(cuò)!令人印象深刻的是,網(wǎng)絡(luò)知道這張照片中有一個(gè)穿著白色 T 恤的男人。另外雖然圖說的句子語(yǔ)法有些錯(cuò)誤(我相信通過更多的訓(xùn)練可以修正這些錯(cuò)誤),但基本的要點(diǎn)都抓住了。
如果輸入的圖像包含網(wǎng)絡(luò)從未見過的東西,它往往會(huì)失敗。例如,我很好奇網(wǎng)絡(luò)會(huì)給 iPhone X 的圖像貼上什么樣的標(biāo)簽。
效果不太好。但總的來說,我對(duì)其性能非常滿意,這為我們?cè)趯W(xué)習(xí)生成圖說時(shí),使用網(wǎng)絡(luò)所開發(fā)的「表示」構(gòu)建其他功能提供了良好的基礎(chǔ)。
回想一下我們?nèi)绾螌?duì)由圖像表示得到的圖說進(jìn)行解碼。我們將該表示提供給 LSTM/GRU 網(wǎng)絡(luò),生成一個(gè)輸出,將輸出解釋為第一個(gè)單詞,然后將第一個(gè)單詞返回給網(wǎng)絡(luò)以生成第二個(gè)單詞。這個(gè)過程一直持續(xù)到網(wǎng)絡(luò)生成一個(gè)表示句子結(jié)束的特殊標(biāo)記為止。
為了將單詞反饋到網(wǎng)絡(luò)中,我們需要將單詞轉(zhuǎn)換為表示,再輸入給網(wǎng)絡(luò)。這意味著,如果輸入層包含 300 個(gè)神經(jīng)元,那么對(duì)于所有圖說中的 8000 多個(gè)不同的單詞,我們需要有一個(gè)唯一指定那個(gè)單詞的「300」數(shù)字。將單詞字典轉(zhuǎn)換成數(shù)字表示的過程,就稱為詞嵌入(或詞表示)。
我們可以下載和使用已經(jīng)存在的詞嵌入,如 word2vec 或 GLoVE。但在本例中,我們從零開始學(xué)習(xí)一個(gè)詞嵌入。我們從隨機(jī)生成的詞嵌入開始,并探索我們的網(wǎng)絡(luò)在完成訓(xùn)練時(shí)從單詞中學(xué)到了什么。
由于無法想象 100 維的數(shù)字空間,我們將使用一種稱為 t-SNE 的神奇技術(shù)將學(xué)到的詞嵌入在二維空間可視化。t-SNE 是一種降維技術(shù),它試圖使高維空間中的鄰域不變地投射為低維空間中的鄰域。
詞嵌入的可視化
讓我們來看看圖說解碼器所學(xué)習(xí)到的詞嵌入空間(不像其他語(yǔ)言任務(wù)中有數(shù)百萬個(gè)單詞和句子,我們的解碼器在訓(xùn)練數(shù)據(jù)集中只看到了大約 3 萬個(gè)句子)。
因此,我們的網(wǎng)絡(luò)已經(jīng)了解到像「play」、「plays」和「playing」這樣的詞匯是非常相似的(它們具有相似的表示,如紅色箭頭所示的密集聚類)。讓我們看看這個(gè)二維空間中的另一個(gè)區(qū)域:
這個(gè)區(qū)域似乎有一堆數(shù)字——「two」、「three」、「four」、「five」等等。再看另一個(gè):
上圖,它知道「people」和「children」這兩個(gè)單詞相似。而且,它還隱晦地推斷出了物體的形狀。
相似詞
我們可以使用 100 維表示來構(gòu)建一個(gè)函數(shù),該函數(shù)可找出與輸入單詞最相似的單詞。它的工作原理很簡(jiǎn)單:采用 100 維的表示,并找出它與數(shù)據(jù)庫(kù)中所有其他單詞的余弦相似度。
讓我們來看看與「boy」最相似的單詞:
結(jié)果不錯(cuò)。除「Rider」外,但「kids」、「kid」和「toddler」都是正確的。
這個(gè)網(wǎng)絡(luò)認(rèn)為與「chasing」相似的詞匯是:
「Chases」是可以理解的,但我疑惑的是為什么它認(rèn)為「police」與「chasing」類似。
單詞類比(Word analogies)
關(guān)于詞嵌入的一個(gè)振奮人心的事實(shí)是,你可以對(duì)它們進(jìn)行微積分計(jì)算。你可以用兩個(gè)單詞(如「king」和「queen」)減去它們的表示來得到一個(gè)方向。當(dāng)你把這個(gè)方向應(yīng)用到另一個(gè)詞的表示上(如「man」),你會(huì)得到一個(gè)與實(shí)際的類比詞(比如「woman」)很接近的表示。這就是為什么 word2vec 一經(jīng)推出就如此受歡迎:
via https://www.tensorflow.org/images/linear-relationships.png
我很好奇通過圖說解碼器學(xué)習(xí)到的表示是否具有類似的屬性。盡管由于訓(xùn)練數(shù)據(jù)并不大(大約 3 萬個(gè)句子)我對(duì)結(jié)果持懷疑態(tài)度,但我還是嘗試了一下。
網(wǎng)絡(luò)學(xué)到的類比并不完美(由于有些單詞書面上出現(xiàn)的次數(shù)<10次,因此網(wǎng)絡(luò)沒有足夠的信息可供學(xué)習(xí)),這種情況下我不得不仔細(xì)去看,但是發(fā)現(xiàn)仍有一些類比。
如果「riding」對(duì)應(yīng)「sitting」,那么「walking」對(duì)應(yīng)什么呢?網(wǎng)絡(luò)認(rèn)為應(yīng)該是「laying」(這個(gè)結(jié)果還不錯(cuò)!)
同樣,如果「man」的復(fù)數(shù)是「men」,那么「woman」的復(fù)數(shù)應(yīng)該是什么呢:
第二個(gè)結(jié)果是「women」,相當(dāng)不錯(cuò)了。
最后,如果「grass」對(duì)應(yīng)「green」,那么「sky」對(duì)應(yīng)什么呢:
網(wǎng)絡(luò)認(rèn)為「sky」對(duì)應(yīng)「silver」或「grey」的,雖然結(jié)果中沒有出現(xiàn)「blue」,但它給的結(jié)果都是顏色詞。令人驚訝的是,這個(gè)網(wǎng)絡(luò)還能夠推斷顏色的方向。
如果詞表示將類似的單詞聚類在一起,那么圖像表示(Inception支持的圖像編碼器輸出)呢?我將相同的 t-SNE 技術(shù)應(yīng)用于圖像表示(在圖說解碼器的第一步中作為輸入的 300 維度的張量)。
可視化
這些點(diǎn)是不同圖像的表示(我沒有使用全部的 8K 圖像,只使用了大約 100 張圖像樣本)。紅色箭頭指向附近一組表示的聚類。
賽車的圖像被聚類在一起。
孩子們?cè)谏?草地玩耍的圖像也被聚類在一起。
籃球運(yùn)動(dòng)員的圖像也被聚類在一起。
查找與輸入圖像相似的圖像
對(duì)于查找相似單詞的任務(wù),我們受限于在測(cè)試集詞匯表中尋找相似的單詞(如果測(cè)試集中不存在某個(gè)單詞,我們的圖說解碼器就不會(huì)學(xué)習(xí)該單詞的嵌入)。然而,對(duì)于類似的圖像任務(wù),我們有一個(gè)圖像表示生成器,它可以接收任何輸入圖像并生成其編碼。
這意味著我們可以使用余弦相似度的方法來構(gòu)建一個(gè)按圖像搜索的功能,如下所示:
步驟 1:獲取數(shù)據(jù)庫(kù)或目標(biāo)文件夾中的所有圖像,并存儲(chǔ)它們的表示(表示由圖像解碼器給出);
步驟 2:當(dāng)用戶希望搜索與已有圖像最相似的圖像時(shí),可以輸入新圖像的表示,并在數(shù)據(jù)庫(kù)中找到與之最接近的圖像(數(shù)據(jù)庫(kù)由余弦相似度給出)。
谷歌圖像就可能會(huì)正式使用這種(或類似的)方法來支持其反向圖像搜索功能。
讓我們看看這個(gè)網(wǎng)絡(luò)是如何工作的。我點(diǎn)擊了下面這張我在 Goa 度假時(shí)拍的照片。(PS:我愛 Goa!)
注意,這張圖片是我自己的,而我們使用的模型此前從未見過這張圖片。當(dāng)我查詢類似的圖像時(shí),網(wǎng)絡(luò)從Flickr8K 數(shù)據(jù)集中輸出如下圖像:
是不是很像?我沒想到該模型會(huì)有這么好的表現(xiàn),但它確實(shí)做到了!深度神經(jīng)網(wǎng)絡(luò)簡(jiǎn)直太棒了?。?a target="_blank" rel=nofollow>https://www.youtube.com/watch?v=Y-WgVcWQYs4)
在最后一部分中,我們將反向運(yùn)行圖說生成器。因此,我們不是獲取圖像并為其生成圖說,而是輸入圖說(文本描述)來找到與之最匹配的圖像。
聽起來好得令人難以置信?當(dāng)然可以相信!我們是這樣做的:
步驟 1:首先輸入的是一個(gè)完全隨機(jī)的 300 維張量,而不是一個(gè)來自編碼器的 300 維圖像表示;
步驟 2:凍結(jié)整個(gè)網(wǎng)絡(luò)的所有層(例如引導(dǎo) PyTorch 不要對(duì)梯度進(jìn)行計(jì)算);
步驟 3:假設(shè)隨機(jī)生成的輸入張量來自圖像編碼器,將其輸入到圖說解碼器中;
步驟 4:獲取給定隨機(jī)輸入時(shí)網(wǎng)絡(luò)生成的圖說,并將其與用戶提供的圖說進(jìn)行比較;
步驟 5:比較生成的圖說和用戶提供的圖說,并對(duì)二者存在損失進(jìn)行計(jì)算;
步驟 6:為輸入張量找到梯度,使損失最小化(例如,在哪個(gè)方向以及 300 維數(shù)中的每個(gè)數(shù)值應(yīng)該改變多少,從而使得在將張量輸入到圖說解碼器時(shí),圖說與用戶提供的圖說接近);
步驟 7:根據(jù)梯度改變輸入張量的方向(學(xué)習(xí)率所給定的一小步);
繼續(xù)步驟 4 到步驟 7,直到收斂或當(dāng)損失低于某個(gè)閾值時(shí)為止
最后一步:取最終的輸入張量,并利用它的值,通過余弦相似度找到離它最近的圖像(以 300 維表示的步速);
通過這樣做,我們得到的結(jié)果相當(dāng)神奇:
我搜索了「一只狗」,這是網(wǎng)絡(luò)找到的圖像:
搜索「一個(gè)微笑的男孩」:
最后,當(dāng)我搜索:
前兩個(gè)結(jié)果是:
以及
這可真是讓人大開眼界,不是嗎?
提醒一下,大家可以從我的 Github 存儲(chǔ)庫(kù)(https://github.com/paraschopra/one-network-many-uses)中下載完成所有這些操作的代碼。這個(gè)存儲(chǔ)庫(kù)包括了用于數(shù)據(jù)預(yù)處理、模型描述、預(yù)訓(xùn)練的圖說生成網(wǎng)絡(luò)、可視化的代碼,但不包括 Flickr8K 數(shù)據(jù)集或圖說——這些需要單獨(dú)下載(https://forms.illinois.edu/sec/1713398)。
希望你喜歡這篇文章。如果你想進(jìn)行更深入的實(shí)操,這里有一個(gè)挑戰(zhàn):基于給定的描述生成圖像。這就好比是由一個(gè)隨機(jī)的起點(diǎn)來生成一個(gè)與用戶提供的圖說匹配的 300 維圖像表示一樣,但是你可以更進(jìn)一步,從零開始為用戶提供的圖說生成一個(gè)圖像嗎?
這比本文中的操作要難 10 倍,但我感覺這是可行的。如果有這樣一個(gè)服務(wù),它不僅可以搜索與文本對(duì)應(yīng)的圖像,而且能夠動(dòng)態(tài)生成圖像,那該有多酷啊!
在未來,如果谷歌圖像實(shí)現(xiàn)了這個(gè)功能,并能夠?yàn)椴淮嬖诘膱D像提供結(jié)果(比如「兩只獨(dú)角獸在披薩做成的地毯上飛翔」),我都不會(huì)感到驚訝。
就這樣。我希望你能夠在「表示」的世界安然而快樂地遨游。
via :https://towardsdatascience.com/one-neural-network-many-uses-image-captioning-image-search-similar-image-and-words-in-one-model-1e22080ce73d 雷鋒網(wǎng) AI 科技評(píng)論 編譯
雷峰網(wǎng)原創(chuàng)文章,未經(jīng)授權(quán)禁止轉(zhuǎn)載。詳情見轉(zhuǎn)載須知。