你將學(xué)習(xí)到的內(nèi)容:本文將深入探討Transformer架構(gòu),這是當(dāng)今幾乎所有尖端大型語言模型架構(gòu)的核心組成部分。 首先,我們將簡(jiǎn)要回顧一些與自然語言處理(NLP)相關(guān)的基本概念,隨后逐步解析Transformer的工作原理。 適用人群:本文適合對(duì)自然語言處理(NLP)感興趣的任何人閱讀。 文章難度:盡管本文并不復(fù)雜,但由于涉及眾多概念,可能對(duì)新手來說有一定的難度。 先決條件:為了更好地理解本文內(nèi)容,大家需要對(duì)標(biāo)準(zhǔn)神經(jīng)網(wǎng)絡(luò)有基本的工作理解,還需要對(duì)嵌入、編碼器和解碼器有初步認(rèn)識(shí)。 Transformer之前的NLP簡(jiǎn)史:在深入探討Transformer之前,我們簡(jiǎn)要介紹一些必要的概念和技術(shù)背景。 如果你已經(jīng)熟悉這些內(nèi)容,可以選擇跳過此部分。其中,詞向量嵌入是理解自然語言處理的基礎(chǔ),它通過將單個(gè)單詞轉(zhuǎn)換為向量來代表其含義。 詞匯向量嵌入器的職責(zé):將詞匯轉(zhuǎn)化為數(shù)字,以某種方式捕捉詞匯的普遍含義。 雖然具體的實(shí)現(xiàn)方法可能因技術(shù)而異,但最終生成的成果可以視作一個(gè)“詞空間”,這個(gè)空間遵循著一定的邏輯和關(guān)系。 單詞本身在數(shù)學(xué)上難以直接運(yùn)算,但蘊(yùn)含單詞信息的向量以及它們之間形成的關(guān)聯(lián),卻便于數(shù)學(xué)操作。 這種將單詞轉(zhuǎn)化為向量的過程,我們通常稱之為“嵌入”。Word2Vec,作為自然語言處理領(lǐng)域的一篇標(biāo)志性論文,旨在生成具備特定實(shí)用特性的嵌入。 研究者們希望單詞之間能夠進(jìn)行代數(shù)運(yùn)算,而Word2Vec正是為了實(shí)現(xiàn)這一目標(biāo)而創(chuàng)建的。 利用Word2Vec,當(dāng)你嵌入“king”的向量,減去“man”的嵌入向量,再加上“woman”的嵌入向量,你將得到一個(gè)與“queen”含義相近的向量。
隨著技術(shù)的不斷進(jìn)步,詞嵌入仍然扮演著至關(guān)重要的角色,其中GloVe、Word2Vec和FastText都是備受推崇的選擇。雖然子詞嵌入通常展現(xiàn)出比全詞嵌入更強(qiáng)大的性能,但這一話題已超出了本文范圍。 另外大家想更進(jìn)一步學(xué)習(xí)機(jī)器學(xué)習(xí)、深度學(xué)習(xí)、神經(jīng)網(wǎng)絡(luò)技術(shù)的可以看看以下文章(文章中提到的資料都打包好了,都可以直接添加小助手獲取) < 人工智能資料分享 > 人工智能60天學(xué)習(xí)計(jì)劃(點(diǎn)擊圖片即可跳轉(zhuǎn)) 深度學(xué)習(xí)中文教程書(點(diǎn)擊圖片即可跳轉(zhuǎn)) 神經(jīng)網(wǎng)絡(luò)最全學(xué)習(xí)資料(點(diǎn)擊圖片即可跳轉(zhuǎn)) 遞歸神經(jīng)網(wǎng)絡(luò)(RNNs) 當(dāng)我們能夠?qū)卧~轉(zhuǎn)換為具有特定意義的數(shù)字向量時(shí),便可以開始深入分析單詞序列。 早期的一種有效策略是利用遞歸神經(jīng)網(wǎng)絡(luò)(RNNs),這種網(wǎng)絡(luò)能夠訓(xùn)練自身在順序輸入上循環(huán)運(yùn)行,從而捕捉序列中的依賴關(guān)系。
RNN的示意結(jié)構(gòu)(假設(shè)有3個(gè)隱藏神經(jīng)元并用于處理2個(gè)輸入):圖中紅色箭頭表示遞歸連接,它連接著來自后續(xù)遞歸層的信息。藍(lán)色箭頭表示內(nèi)部連接,類似于密集層。為了說明起見,我們復(fù)制了神經(jīng)網(wǎng)絡(luò),但請(qǐng)記住,網(wǎng)絡(luò)實(shí)際上是反饋到自身的,這意味著第二個(gè)(及后續(xù))模塊的參數(shù)與第一個(gè)模塊相同。 與傳統(tǒng)神經(jīng)網(wǎng)絡(luò)不同,遞歸神經(jīng)網(wǎng)絡(luò)(RNNs)通過在循環(huán)連接中重用相同的參數(shù),能夠處理任意長(zhǎng)度的序列。 這意味著,無論是長(zhǎng)度為10的序列還是長(zhǎng)度為100的序列,RNNs都只需要相同數(shù)量的參數(shù)。 這種網(wǎng)絡(luò)結(jié)構(gòu)因其靈活性而被廣泛應(yīng)用于多種建模問題,這些問題通??梢詺w納為序列到序列建模、序列到向量建模、向量到序列建模,以及序列到向量再到序列的建模。 不同建模策略中RNN的一些應(yīng)用概念圖:序列到序列模型可能用于預(yù)測(cè)文本補(bǔ)全中的下一個(gè)單詞;序列到向量模型可能用于評(píng)估客戶對(duì)評(píng)論的滿意度;向量到序列模型可能用于將圖像壓縮為向量,并要求模型將該圖像描述為一系列文本;序列到向量到序列模型可能用于文本翻譯,需要理解句子,將其壓縮為某種表示,然后在另一種語言中構(gòu)建該壓縮表示的翻譯。 盡管遞歸神經(jīng)網(wǎng)絡(luò)(RNNs)理論上能夠處理無限長(zhǎng)度的序列,但這一承諾在實(shí)際應(yīng)用中并不完全實(shí)用。 由于RNNs的每一層都共享相同的權(quán)重,它們?cè)谔幚黹L(zhǎng)序列時(shí)容易出現(xiàn)“遺忘”輸入內(nèi)容的問題。 因此,RNNs在實(shí)際應(yīng)用中通常只適用于處理非常短的單詞序列。 為了克服這一局限性,研究者們?cè)鴩L試通過引入“門控”和“泄露”機(jī)制來改進(jìn)RNNs。 其中最著名且有效的改進(jìn)是長(zhǎng)短期記憶網(wǎng)絡(luò)(LSTM),我們將在下一節(jié)中對(duì)其進(jìn)行詳細(xì)描述。 長(zhǎng)短期記憶(LSTMs) LSTM(長(zhǎng)短期記憶網(wǎng)絡(luò))的設(shè)計(jì)初衷是為了增強(qiáng)遞歸神經(jīng)網(wǎng)絡(luò)在保留重要信息方面的能力。 LSTM具備短期和長(zhǎng)期記憶功能,能夠在序列的任意位置中,選擇性地保留或遺忘某些信息到其長(zhǎng)期記憶中。 LSTM LSTM的三個(gè)關(guān)鍵子組件 LSTM(長(zhǎng)短期記憶網(wǎng)絡(luò))的核心概念體現(xiàn)在其三個(gè)關(guān)鍵的子組件上:“遺忘門”負(fù)責(zé)篩選并遺忘部分舊的長(zhǎng)期記憶信息,“輸入門”則負(fù)責(zé)將新的信息加入到長(zhǎng)期記憶中,而“輸出門”則負(fù)責(zé)控制從長(zhǎng)期記憶中提取的信息,并將其作為下一次迭代的短期記憶使用。
LSTM及其類似架構(gòu)如GRU,相較于經(jīng)典的RNN,展現(xiàn)出了顯著的改進(jìn)。 它們將記憶作為一個(gè)獨(dú)立的概念,能夠檢查和提取關(guān)鍵信息,這使得它們?cè)谔幚硇蛄袛?shù)據(jù)方面更具優(yōu)勢(shì)。 然而,盡管LSTM能夠建模更長(zhǎng)的序列,但在許多語言建模任務(wù)中,它們?nèi)悦媾R記憶遺忘的問題。 此外,由于LSTM和RNN一樣,都依賴于前序輸入進(jìn)行逐步計(jì)算,因此它們的訓(xùn)練過程難以并行化,導(dǎo)致訓(xùn)練速度相對(duì)較慢。 通過對(duì)齊實(shí)現(xiàn)注意力機(jī)制 劃時(shí)代的論文《通過聯(lián)合學(xué)習(xí)對(duì)齊和翻譯實(shí)現(xiàn)神經(jīng)機(jī)器翻譯》普及了注意力機(jī)制的概念,并為Transformer中的多頭自注意力機(jī)制奠定了基礎(chǔ)。 簡(jiǎn)單來說,注意力機(jī)制允許模型在生成輸出時(shí)查看所有潛在的輸入,并根據(jù)需要選擇性地關(guān)注與當(dāng)前輸出相關(guān)的輸入。換句話說,它賦予了模型決定哪些輸入在特定時(shí)刻是重要或不重要的能力。 這種方法在翻譯任務(wù)中產(chǎn)生了深遠(yuǎn)的影響。 它使模型能夠更準(zhǔn)確地捕捉輸入中的關(guān)鍵信息,從而在翻譯過程中展現(xiàn)出前所未有的性能。 正方形代表詞匯向量嵌入,圓圈代表中間向量表示。紅色和藍(lán)色的圓圈是循環(huán)網(wǎng)絡(luò)的隱藏狀態(tài),而白色的圓圈是通過對(duì)齊機(jī)制由注意力機(jī)制創(chuàng)建的隱藏狀態(tài)。關(guān)鍵點(diǎn)是,注意力機(jī)制可以選擇在任何給定步驟中呈現(xiàn)給輸出的正確輸入。 另外大家想更進(jìn)一步學(xué)習(xí)機(jī)器學(xué)習(xí)、深度學(xué)習(xí)、神經(jīng)網(wǎng)絡(luò)技術(shù)的可以看看以下文章(文章中提到的資料都打包好了,都可以直接添加小助手獲取) < 人工智能資料分享 > 人工智能60天學(xué)習(xí)計(jì)劃(點(diǎn)擊圖片即可跳轉(zhuǎn)) 深度學(xué)習(xí)中文教程書(點(diǎn)擊圖片即可跳轉(zhuǎn)) 神經(jīng)網(wǎng)絡(luò)最全學(xué)習(xí)資料(點(diǎn)擊圖片即可跳轉(zhuǎn)) Transformer 在前面的章節(jié)中,我們了解了一些基礎(chǔ)。 接下來,我們將重點(diǎn)轉(zhuǎn)向Transformer,這是一個(gè)集結(jié)了前人的成功智慧和新穎思想的杰作,它徹底革新了自然語言處理領(lǐng)域。 Transformer 我們將逐步拆解Transformer的每一個(gè)組成部分,深入探討每個(gè)模塊的工作原理。 雖然涉及的內(nèi)容相當(dāng)豐富,但我們會(huì)盡量避免復(fù)雜的數(shù)學(xué)推導(dǎo),確保概念易于理解。 架構(gòu) Transformer本質(zhì)上是一種編碼器/解碼器風(fēng)格的模型,與我們之前探討的序列到向量再到序列的模型類似。 編碼器負(fù)責(zé)接收輸入并將其轉(zhuǎn)化為一個(gè)能夠表達(dá)整個(gè)輸入意義的緊湊表示,而解碼器則基于這個(gè)嵌入,遞歸地構(gòu)建并生成輸出。
輸入嵌入和位置編碼原始圖中的輸入嵌入 Transformer的輸入嵌入策略與我們之前討論的方法類似,它利用類似于Word2Vec的詞空間嵌入器將輸入單詞全部轉(zhuǎn)換為向量。 這些嵌入向量是與模型一同進(jìn)行訓(xùn)練的,實(shí)際上可以看作是一個(gè)隨模型學(xué)習(xí)而不斷優(yōu)化的查找表。 在初始階段,每個(gè)單詞都對(duì)應(yīng)一個(gè)隨機(jī)初始化的向量,但隨著模型的學(xué)習(xí)過程,這些向量會(huì)根據(jù)每個(gè)單詞在上下文中的表現(xiàn)而逐漸調(diào)整和優(yōu)化。 與遞歸神經(jīng)網(wǎng)絡(luò)(RNNs)逐步處理序列的方式不同,Transformers能夠一次性地編碼整個(gè)輸入序列。 然而,由于這種處理方式,Transformer編碼器可能會(huì)失去有關(guān)輸入單詞之間順序位置的信息。 為了彌補(bǔ)這一缺陷,Transformer引入了位置編碼,以確保模型能夠識(shí)別序列中單詞的順序。 ''' Plotting positional encoding for each index. A positional encoding for a single token would be a horizontal row in the image
inspired by https:///a-gentle-introduction-to-positional-encoding-in-transformer-models-part-1/ '''
import numpy as np import matplotlib.pyplot as plt
#these would be defined based on the vector embedding and sequence sequence_length = 512 embedding_dimension = 1000
#generating a positional encodings def gen_positional_encodings(sequence_length, embedding_dimension): #creating an empty placeholder positional_encodings = np.zeros((sequence_length, embedding_dimension))
#itterating over each element in the sequence for i in range(sequence_length):
#calculating the values of this sequences position vector #as defined in section 3.5 of the attention is all you need #paper: https:///pdf/1706.03762.pdf for j in np.arange(int(embedding_dimension/2)): denominator = np.power(sequence_length, 2*j/embedding_dimension) positional_encodings[i, 2*j] = np.sin(i/denominator) positional_encodings[i, 2*j+1] = np.cos(i/denominator)
return positional_encodings
#rendering fig, ax = plt.subplots(figsize=(15,5)) ax.set_ylabel('Sequence Index') ax.set_xlabel('Positional Encoding') cax = ax.matshow(gen_positional_encodings(sequence_length, embedding_dimension)) fig.colorbar(cax, pad=0.01)
位置向量值相對(duì)于序列中不同索引的變化:K代表序列中的索引,圖形代表向量中的值。 為了彌補(bǔ)Transformer在處理序列時(shí)可能丟失的單詞位置信息,Transformer還引入了位置編碼器。 這個(gè)編碼器負(fù)責(zé)生成一個(gè)向量,該向量編碼了特定單詞在序列中的位置信息。 該系統(tǒng)巧妙地利用正弦和余弦函數(shù)來聯(lián)合編碼位置,使得位置信息得以連續(xù)和平滑地表達(dá)。 如果你想深入了解這種編碼方式的工作原理,可以閱讀相關(guān)的專業(yè)文章。 雖然你可能會(huì)擔(dān)心,將這樣的波形添加到單詞嵌入中是否會(huì)掩蓋原始嵌入的一些意義,導(dǎo)致模型混淆。 但實(shí)際上,神經(jīng)網(wǎng)絡(luò)(特別是Transformer,憑借其可學(xué)習(xí)的參數(shù))非常擅長(zhǎng)處理和理解平滑且連續(xù)的函數(shù)。 因此,對(duì)于足夠大的模型來說,這種位置編碼方式并不會(huì)對(duì)模型性能產(chǎn)生負(fù)面影響。 相反,它幫助模型更好地捕捉序列中單詞的位置信息,從而提高了模型的性能。 多頭自注意力機(jī)制:核心組件解析 在Transformer架構(gòu)中,多頭自注意力機(jī)制無疑是最為關(guān)鍵的子組件。 原始圖中的多頭自注意力機(jī)制 然而,將其簡(jiǎn)單地稱為“注意力”機(jī)制可能略顯誤導(dǎo),因?yàn)樗鼘?shí)際上更多地扮演了“關(guān)聯(lián)”和“情境化”的角色。 它使得單詞之間能夠相互交互,將輸入的每個(gè)單詞的嵌入向量列表轉(zhuǎn)化為一個(gè)矩陣,這個(gè)矩陣能夠全面表達(dá)整個(gè)輸入序列的深層含義。 簡(jiǎn)單來說多頭自注意力機(jī)制通過數(shù)學(xué)方式將不同單詞的向量組合起來,形成一個(gè)矩陣,該矩陣編碼了整個(gè)輸入的更深層次的意義。 多頭自注意力機(jī)制的運(yùn)行過程可以分為四個(gè)主要步驟:
步驟 1) 創(chuàng)建查詢、鍵和值 首先,我們需要理解“查詢”、“鍵”和“值”這三個(gè)概念。盡管它們的命名可能讓人聯(lián)想到數(shù)據(jù)庫中的概念,但實(shí)際上在自注意力機(jī)制中,這些術(shù)語只是抽象地表示了嵌入輸入的不同方面。 查詢、鍵和值本質(zhì)上是輸入嵌入的不同變換形式,它們將在后續(xù)步驟中用于相互之間的關(guān)聯(lián)計(jì)算。
上圖所展示的密集網(wǎng)絡(luò)結(jié)構(gòu)包含了多頭自注意力機(jī)制中的全部可學(xué)習(xí)參數(shù)。 多頭自注意力機(jī)制實(shí)際上是一個(gè)可學(xué)習(xí)的函數(shù),模型通過學(xué)習(xí)如何調(diào)整這些參數(shù)來優(yōu)化輸入(即查詢、鍵和值)在最終建模任務(wù)中的表現(xiàn)。 在多頭自注意力機(jī)制中,步驟2是將查詢、鍵和值分割成多個(gè)“頭”。 這一步是為了在實(shí)際進(jìn)行情境化自注意力計(jì)算之前,增加模型的表示能力。 核心思想是,通過多個(gè)不同的“頭”來捕捉輸入數(shù)據(jù)中不同維度的關(guān)聯(lián)信息,而不僅僅依賴于單一的關(guān)聯(lián)方式。 這樣做的好處是能夠編碼更加微妙和復(fù)雜的語義信息,從而提升模型在最終任務(wù)上的性能。
多頭自注意力機(jī)制 步驟 3) 注意力頭 現(xiàn)在,我們有了被分割并傳遞給注意力頭的查詢、鍵和值的子組件,接下來將探討注意力頭是如何利用這些值來生成情境化結(jié)果的。 在《Attention is All You Need》這篇論文中,這一過程是通過矩陣乘法來完成的。
在矩陣乘法中,一個(gè)矩陣的行與另一個(gè)矩陣的列逐對(duì)進(jìn)行點(diǎn)積運(yùn)算,從而生成一個(gè)結(jié)果矩陣。 在注意力機(jī)制中,查詢和鍵的矩陣通過乘法運(yùn)算相結(jié)合,產(chǎn)生了一個(gè)我們稱之為“注意力矩陣”的結(jié)果。 使用查詢和鍵來計(jì)算注意力矩陣。請(qǐng)注意,鍵被轉(zhuǎn)置以允許矩陣乘法產(chǎn)生正確的注意力矩陣形狀。 盡管這種操作在表面上看似簡(jiǎn)單,但其影響力卻不容忽視。在此步驟中,使用矩陣乘法使得每個(gè)單詞的表示都能與其他單詞的表示進(jìn)行交互。 由于查詢和鍵是由密集網(wǎng)絡(luò)定義的,注意力機(jī)制學(xué)會(huì)了如何調(diào)整查詢和鍵的表示,以優(yōu)化注意力矩陣的內(nèi)容。 一旦我們得到了注意力矩陣,就可以將其與值矩陣相乘。 這一步驟有三個(gè)主要目的:
重要的修正 在注意力機(jī)制中,注意力矩陣在與值矩陣相乘之前會(huì)經(jīng)歷一個(gè)關(guān)鍵的步驟——按行進(jìn)行softmax運(yùn)算。 這一數(shù)學(xué)細(xì)節(jié)至關(guān)重要,因?yàn)樗鼜氐赘淖兞俗⒁饬仃嚺c值矩陣之間的交互方式,并賦予了其更深層的概念意義。 經(jīng)過softmax處理后,注意力矩陣的每一行都轉(zhuǎn)化為了一個(gè)概率分布,每個(gè)元素表示對(duì)應(yīng)位置上的權(quán)重。 這種概率化的表示與我在另一篇文章中詳細(xì)闡述的對(duì)齊注意力概念高度吻合,都強(qiáng)調(diào)了輸入序列中不同部分之間的相對(duì)重要性。 這種處理方式不僅增強(qiáng)了模型的解釋性,還使其能夠更精準(zhǔn)地捕捉序列中的關(guān)鍵信息。 從我的“注意力對(duì)齊”文章中可以看到,每一行都是一個(gè)概率分布,總和為1,這強(qiáng)制使最重要的事物與其他重要事物相關(guān)聯(lián)。 這一細(xì)節(jié)在Transformer的廣泛討論中經(jīng)常被忽視,但實(shí)際上是Transformer架構(gòu)中至關(guān)重要的一個(gè)環(huán)節(jié),因?yàn)樗鼘⒛:年P(guān)聯(lián)性轉(zhuǎn)化為稀疏且富含意義的選擇。 注意力矩陣(即查詢和鍵的矩陣乘法結(jié)果)乘以值矩陣,得出注意力機(jī)制的最終結(jié)果。由于注意力矩陣的形狀,結(jié)果將與值矩陣具有相同的形狀。請(qǐng)記住,這是來自單個(gè)注意力頭的結(jié)果。 多頭自注意力機(jī)制 步驟 4) 構(gòu)建最終輸出 在之前的步驟中,我們利用查詢、鍵和值構(gòu)建了一個(gè)新結(jié)果矩陣,這個(gè)矩陣的形狀與值矩陣相同,但包含了更豐富的上下文信息。 值得注意的是,每個(gè)注意力頭僅關(guān)注輸入空間中的特定子組件(這些子組件是沿著特征軸劃分的)。
接下來,每個(gè)注意力頭都會(huì)輸出不同的結(jié)果矩陣。為了將這些結(jié)果整合起來,我們將它們沿著特征軸拼接(concatenate)在一起。 每個(gè)注意力頭的結(jié)果會(huì)被連接在一起 這樣得到的最終輸出矩陣與原始輸入矩陣的形狀完全一致。 然而,與輸入矩陣中每行直接與單個(gè)單詞相關(guān)聯(lián)不同,這個(gè)輸出矩陣經(jīng)過了多頭自注意力機(jī)制的處理,因此包含了更為抽象和豐富的信息。
|
|