ในตอนนี้เราจะมาพูดถึง Attention Module ซึ่งถือเป็นหัวใจหลักของ Transformer กันครับ
Attention Module
Attention ใน Transformer จะต่างจาก Attention ใน seq2seq ที่กล่าวมาข้างต้นหลายประการ ประการแรกคือไม่ใช่เป็นการหา attention vector ของส่วน decoder จากส่วน encoder เพียงทางเดียวเท่านั้น แต่ทุกๆ หน่วยของข้อมูลจะทำ attention กันเองด้วย สิ่งนี้เรียกว่า Self-Attention และการทำ Attention จะเป็นแบบ Scaled Dot-Product Attention ที่เสริมด้วย Multi-Head Attention ซึ่งมีรายละเอียดดังนี้ครับ
Scaled Dot-Product Attention
ในที่นี้จะมาขยายความ Attention จากที่กล่าวมาแล้วให้เป็น Attention ที่ใช้ใน Transformer กันครับ โดยเริ่มจากการแบ่งประเภท vector เป็น query กับ key และ value ซึ่ง query ในที่นี้ จะเหมือนกับ q ในหัวข้อที่แล้ว ส่วน p ในหัวข้อที่แล้ว จะเหมือนเป็นทั้ง key (k) และ value (v) ไปพร้อมกัน โดย k คือ vector ที่นำไปทำ dot product กับ q เพื่อดูว่าควรจะใส่ใจกับตำแหน่งไหน และ v จะเป็นค่าที่นำมาใช้นั่นเอง เปรียบเสมือนกับเรามีหีบ (k, v) อยู่หลายใบ โดย k เป็นกุญแจล็อคหีบ และ v เป็นของที่อยู่ข้างใน ส่วน q ก็คือลูกกุญแจที่นำมาไขหีบ ถ้า q เข้ากับ k ได้ดี ก็จะสามารถนำ v ไปใช้ได้มาก ซึ่งการทำ Attention ในที่นี้ ก็คือฟังก์ชัน A ที่รับ q กับ K และ V เข้ามา แล้วให้ผลลัพธ์ออกไปเป็น vector ตัวนึงที่เป็นส่วนผสมของ v ต่างๆ โดยที่ให้ความสำคัญกับ v ตามค่าของ k·q หรือจะเขียนเป็นสมการได้ว่า
และอาจเขียนเป็นแผนภาพได้ดังนี้ครับ
ถ้าหากว่าต้องการคำนวณ q หลายๆ ตัว เราก็สามารถทำให้เป็นการคูณ matrix ได้เลย จากสมการข้างบน ก็จะกลายเป็น
โดยที่แต่ละเวคเตอร์ q, k, v คือ row vector ใน Q, K, V ตามลำดับ และการทำ softmax ในที่นี้ก็จะทำตาม row และผล attention vector ของแต่ละ q ก็คือแต่ละ row ใน A(Q, K, V) นั่นเองครับ
ทั้งนี้หาก dimension ของ k ซึ่งเท่ากับ dimension ของ q มีค่าสูง ค่าของ k·q ก็จะสูงตามไปด้วย ซึ่งพอเข้า softmax แล้ว จะไปอยู่ในบริเวณที่มี gradient น้อย ทำให้ยากต่อการ optimization ผู้ทำวิจัยจึงได้ลดขนาดของ k·q ตามจำนวน dimension ของ k ด้วย ดังนี้ครับ
จากการเลือกใช้ Attention แบบ dot product ที่ประหยัดทั้งเวลาและเนื้อที่ในการคำนวณมากกว่า Attention แบบอื่นๆ โดยเพิ่ม scaling factor เข้าไป จึงได้ออกมาเป็น Scaled Dot-Product Attention ซึ่งสมการข้างต้นก็สามารถเขียนเป็นแผนภาพได้ดังนี้ครับ
Multi-Head Attention
จะเห็นว่า Scaled Dot-Product Attention จากหัวข้อที่แล้ว ถ้านำมาใช้เลยทันทีจะมีข้อจำกัดอยู่สองอย่างด้วยกัน อย่างแรกก็คือข้างต้นนี้เป็นการนำค่า Q, K, V มาคำนวณตรงๆ ซึ่งอาจไม่ใช่ representation ที่เหมาะสมสำหรับการทำ Attention เราจึงควรจะให้ระบบมีการเรียนรู้ representation ที่เหมาะสมด้วย โดยการใส่ weight เข้าไป ทำให้ Attention Module กลายเป็นดังนี้ครับ
แต่ถึงกระนั้นก็ยังมีข้อจำกัดอยู่ตรงที่ทุกหน่วยของข้อมูลมีปฏิสัมพันธ์กันได้เพียงแบบเดียว ซึ่งไม่เพียงพอสำหรับงานทั่วไปที่หน่วยต่างๆ ของข้อมูลจะมีความสัมพันธ์กันได้หลายแบบ เช่นประโยคที่ว่า “ฉันเลี้ยงแมว” คำว่า “แมว” กับ “ฉัน” อาจจะมีความสัมพันธ์โดยที่ “แมว” เป็นกรรมตรงของประโยคที่มีประธานคือ “ฉัน” หรือ “ฉัน” คือสิ่งที่แสดงความเป็นเจ้าของของ “แมว” ก็ได้ เพราะฉะนั้น จึงควรจะมี Q, K, V ไว้หลายๆ ชุด ซึ่งจะถูกคูณด้วยค่า weight ที่ต่างกันออกไป เพื่อให้สามารถเรียนรู้ความสัมพันธ์ต่างๆ ได้ จากนั้นจึงทำ Attention ในแต่ละชุด ก่อนที่จะรวมทุกชุดเข้าด้วยกันเป็นข้อมูลเพื่อส่งไปประมวลผลต่อไป โดย Attention ชุดนึง จะเรียกว่าหัวหัวนึง และ Multi-Head Attention คือการนำทุกหัวมารวมกัน ซึ่งเขียนเป็นสมการได้ดังนี้ครับ
การที่มีหลายหัวเช่นนี้ อาจเทียบได้กับ CNN ที่มีหลาย channel ซึ่งแต่ละ channel ก็จะเรียน feature ที่แตกต่างกันไป และดูจะตรงกับภาษิตไทยที่ว่า “หลายหัวดีกว่าหัวเดียว” อยู่เหมือนกัน สุดท้ายแล้ว Multi-Head Attention สามารถสรุปออกมาเป็นภาพได้ดังนี้ครับ
Attention แบบต่างๆ
ใน Transformer จะใช้ Attention ที่ต่างกันสามแบบ ดังนี้ครับ
แบบแรกคือ Self-Attention ปกติ ที่ทุกหน่วยจะทำ Attention กับทุกหน่วย
แบบที่สองคือ Masked Self-Attention ที่แต่ละหน่วยทำ Attention กับเฉพาะข้อมูลที่อยู่ด้านหน้าเท่านั้น โดย Attention ชนิดนี้จะใช้กับส่วน decoder เนื่องจากกระบวนการผลิต output ในตอนใช้งานจริงเป็นการผลิตทีละตัว จึงไม่สามารถนำข้อมูลจากอนาคตมาใช้ได้
ส่วนแบบที่สามคือ Attention ที่เหมือนกับที่ใช้ใน seq2seq ทั่วไป โดยฝั่ง decoder จะเป็นตัว query ข้อมูลจากฝั่ง encoder