@StatsSorceress TL; DR:
ฉันกำลังทำกิจกรรมนี้เพื่อดูว่าฉันสามารถคำนวณหน่วยความจำที่ต้องใช้ตัวเองได้หรือไม่:
การเปิดใช้งาน: 532,752 * 2 * 4 / (1024 ^ 2) = 4.06 MB
พารามิเตอร์: 19,072,984 * 4 / (1024 ^ 2) * 3 = 218.27 MB
เบ็ดเตล็ด: 128 * 9,000 * 4 / (1024 ^ 2) = 4.39 MB
หน่วยความจำทั้งหมด: (4.06 * 128 ) + 218.27 + 4.39 = 742.34 MB
(มีคนโปรดแก้ไขฉันด้วยถ้าไม่ถูกต้อง FYI คุณคูณคูณด้วย 128 แล้วนั่นเป็นเหตุผลว่าทำไมฉันไม่คูณด้วย 128 ข้างบน )
ฉันจะชี้ให้คุณไปที่บทความนี้และวิดีโอที่เกี่ยวข้อง พวกเขาช่วยให้ฉันเข้าใจสิ่งที่เกิดขึ้นมากขึ้น
หมายเหตุ: หน่วยความจำที่จำเป็นในการใช้เครือข่ายสำหรับการคาดการณ์นั้นน้อยกว่าที่จำเป็นสำหรับการฝึกอบรมด้วยเหตุผลสองประการ:
- เมื่อคาดการณ์เราจะส่งภาพไปข้างหน้าผ่านเครือข่ายเท่านั้นและไม่ย้อนกลับ (ดังนั้นเราจะไม่คูณหน่วยความจำ X 3; ดูด้านล่าง)
- มีการคาดการณ์หนึ่งภาพต่อภาพ (ดังนั้นเราจึงไม่จำเป็นต้องเพิ่มจำนวนหน่วยความจำที่จำเป็นสำหรับภาพหนึ่งภาพด้วยขนาดแบตช์เพราะเราไม่ได้ใช้ชุดคำสั่งในการทำนาย)
กระบวนการ (หน่วยความจำการฝึกอบรม)
- คำนวณหน่วยความจำที่จำเป็นในการฝึกอบรมในหนึ่งภาพ
- คูณจำนวนนี้ด้วยจำนวนภาพในแบทช์ของคุณ
( โปรดจำไว้ว่า: ชุดข้อมูล ขนาดเล็กบอกว่าเราใช้ชุดย่อยของข้อมูลของเราคำนวณการไล่ระดับสีและข้อผิดพลาดสำหรับแต่ละภาพในชุดย่อยจากนั้นเฉลี่ยค่าเหล่านี้และก้าวไปข้างหน้าในทิศทางของค่าเฉลี่ยสำหรับ Convnets น้ำหนักและอคติ จำนวนการเปิดใช้งานถูกปิดกั้นด้วยจำนวนภาพในแบทช์ )
ขั้นตอนที่ 1: หน่วยความจำสำหรับ 1 ภาพ
ในการฝึกอบรมหนึ่งภาพคุณต้องจองหน่วยความจำสำหรับ:
พารามิเตอร์โมเดล:
น้ำหนักและอคติในแต่ละชั้นของพวกเขาไล่ระดับสีของพวกเขาและตัวแปรโมเมนตัม (ถ้าอดัม Adagrad, RMSProp ฯลฯ เพิ่มประสิทธิภาพถูกนำมาใช้)
ในการประมาณหน่วยความจำสำหรับสิ่งนี้ให้คำนวณหน่วยความจำที่จำเป็นในการจัดเก็บน้ำหนักและอคติและคูณด้วย 3 (เช่น "คูณ 3" เพราะเรากำลังบอกจำนวนหน่วยความจำที่จำเป็นในการจัดเก็บน้ำหนักและอคติคือ ที่จำเป็นสำหรับการไล่ระดับสีและสำหรับตัวแปรโมเมนตัม)
สมการ:
convolutions:
น้ำหนัก (n) = ความลึก (n) * (kernel_width * kernel_height) * ความลึก (n-1)
อคติ (n) = ความลึก (n)
เลเยอร์ที่เชื่อมต่ออย่างสมบูรณ์ (หนาแน่น):
weights (n) = เอาต์พุต (n) * อินพุต (n)
อคติ (n) = เอาท์พุท (n)
โดยที่nคือเลเยอร์ปัจจุบันและn-1เป็นเลเยอร์ก่อนหน้าและเอาต์พุตคือจำนวนเอาต์พุตจากเลเยอร์ FC และอินพุตคือจำนวนอินพุตไปยังเลเยอร์ FC (หากเลเยอร์ก่อนหน้านี้ไม่ใช่เลเยอร์ที่เชื่อมต่อทั้งหมด จำนวนอินพุตเท่ากับขนาดของเลเยอร์นั้นแบน)
หมายเหตุ:หน่วยความจำสำหรับน้ำหนักและอคติเพียงอย่างเดียวรวมถึงหน่วยความจำสำหรับการเปิดใช้งานสำหรับหนึ่งภาพ (ดูด้านล่าง) คือจำนวนหน่วยความจำทั้งหมดที่คุณต้องการสำหรับการคาดการณ์ (ไม่รวมค่าโสหุ้ยสำหรับหน่วยความจำสำหรับ Convolutions และอื่น ๆ )
- การเปิดใช้งาน (นี่คือ "Blobs" ใน Caffe):
(ฉันใช้คำศัพท์ที่นี่อดทนกับฉัน)
การบิดแต่ละครั้งในชั้นการบิดทำให้เกิดการเปิดใช้งาน" จำนวนพิกเซลในภาพ " (เช่นคุณส่งภาพผ่านการบิดเพียงครั้งเดียวคุณจะได้รับแผนที่คุณลักษณะเดียวซึ่งประกอบด้วยการเปิดใช้งาน " m " โดยที่ " m " คือจำนวนพิกเซลจาก ภาพ / input)
สำหรับเลเยอร์ที่เชื่อมต่ออย่างสมบูรณ์จำนวนการเปิดใช้งานที่คุณสร้างเท่ากับขนาดของเอาต์พุตของคุณ
convolutions:
การเปิดใช้งาน (n) = image_width * image_height * image_num_channels
เลเยอร์ที่เชื่อมต่ออย่างสมบูรณ์ (หนาแน่น):
การเปิดใช้งาน (n) = เอาท์พุท (n)
โปรดทราบว่าการป้อนข้อมูลของคุณเป็นเพียงภาพที่จุดเริ่มต้นของเครือข่าย หลังจากการโน้มน้าวใจมันจะกลายเป็นอย่างอื่น (ฟีเจอร์แผนที่) ดังนั้นแทนที่ "image_width", "image_height" และ "image_num_channels" ด้วย "input_width", "input_height" และ "layer_depth" ให้แม่นยำยิ่งขึ้น (มันง่ายกว่าสำหรับฉันที่จะคิดถึงแนวคิดนี้ในแง่ของภาพ)
เนื่องจากเราต้องเก็บข้อผิดพลาดสำหรับการเปิดใช้งานในแต่ละเลเยอร์ (ใช้ในการย้อนกลับ) เราจึงคูณจำนวนการเปิดใช้งานด้วย 2 เพื่อให้ได้จำนวนเอนทิตีทั้งหมดที่เราต้องการเพื่อให้มีพื้นที่ว่างในพื้นที่เก็บข้อมูลของเรา จำนวนการเปิดใช้งานจะเพิ่มขึ้นตามจำนวนภาพในแบทช์ดังนั้นคุณจึงคูณจำนวนนี้ด้วยขนาดแบทช์
ขั้นตอนที่ 2: หน่วยความจำเพื่อฝึกอบรมแบทช์
รวมจำนวนน้ำหนักและอคติ (เท่า 3) และจำนวนการเปิดใช้งาน (คูณ 2 เท่าของขนาดแบทช์) คูณด้วย 4 และคุณจะได้จำนวนไบต์ที่ต้องใช้ในการฝึกอบรมแบทช์ คุณสามารถหารด้วย 1024 ^ 2 เพื่อให้ได้คำตอบเป็น GB