โอนจากหลายกระเป๋าไปหลายกระเป๋าบน Solana
การโอนแบบจับคู่กระเป๋าเงินบน Solana ทำงานอย่างไร หนึ่งธุรกรรมต่อหนึ่งแถว ค่าธรรมเนียม 0.001 SOL ต่อการโอน และกฎ rent ที่ข้ามแถวแทนที่จะตัดยอดลง

บน Solana มีวิธีขยับเงินจำนวนมากในคราวเดียวอยู่สามแบบ และสามแบบนี้ถูกสับสนกันตลอดเวลา เครื่องมือส่งหลายรายการจ่ายตามรายชื่อจากกระเป๋าเงินใบเดียว เครื่องมือรวบรวมดึงกระเป๋าเงินหลายใบเข้ามาไว้ในใบเดียว แล้วยังเหลืออีกกรณีหนึ่งที่สองแบบแรกพูดแทนไม่ได้เลย
การโอนหลายกระเป๋าไปหลายกระเป๋าบน Solana เก็บผู้ส่งแต่ละรายไว้กับผู้รับของตัวเอง กระเป๋าเงินใบที่ 7 จ่ายให้ใบที่ 7 ใบที่แปดจ่ายให้ใบที่แปด และทั้งสองไม่รู้จักกันเลย
ฟังดูเหมือนรายละเอียดเล็กน้อย จริง ๆ แล้วมันคือความต่างระหว่างการมีแหล่งเงินเดียว กับการมีแหล่งเงินสี่สิบแหล่งที่เป็นอิสระต่อกัน
- หนึ่งแถวคือหนึ่งธุรกรรม กระเป๋าเงินผู้ส่งของแถวนั้นจ่ายทุกอย่างที่อยู่บนแถวนั้น
- ค่าธรรมเนียมแพลตฟอร์ม 0.001 SOL ต่อการโอนหนึ่งครั้ง ค่าธรรมเนียมเครือข่าย 0.000005 SOL
- ผู้รับที่ไม่เคยถือโทเคนตัวนี้มาก่อน เพิ่มเงินมัดจำ rent อีก 0.00203928 SOL
- แถวที่ผ่านการตรวจไม่ได้จะถูกข้ามทั้งแถว ไม่ใช่ถูกตัดยอดลง
สามรูปแบบของการโอนจำนวนมาก
เครื่องมือส่งหลายรายการคือหนึ่งไปหลาย กระเป๋าเงินใบเดียว รายชื่อผู้รับหนึ่งชุด ผู้จ่ายรายเดียว นี่คือรูปแบบที่ใช้กับการแจกโทเคน
เครื่องมือรวบรวมเป็นชุดคือหลายไปหนึ่ง กระเป๋าเงินยี่สิบใบ ปลายทางเดียว และเมื่อจบงานทุกอย่างไปกองอยู่ที่เดียว
เครื่องมือหลายไปหลายคือรูปแบบที่สาม และเป็นแบบเดียวที่รู้จักการจับคู่ นี่คือสิ่งที่เรียกว่าการโอนหลายกระเป๋าไปหลายกระเป๋า แถวแรกมีแหล่งเงินของแถวแรก แถวที่สองมีอีกแหล่งหนึ่ง ไม่มีกองกลาง และแถวหนึ่งไม่ได้ช่วยอุดอีกแถวหนึ่ง
หนึ่งแถวมีค่าใช้จ่ายเท่าไร
บนหนึ่งแถวอาจมีรายการค่าใช้จ่ายได้ถึงสามรายการ และกระเป๋าเงินผู้ส่งของแถวนั้นเป็นคนจ่ายทั้งสามรายการ ไม่มีบัญชีกลางที่คอยเติมเงินให้ ดังนั้นกระเป๋าเงินที่คลุมค่าใช้จ่ายของแถวตัวเองไม่ไหว ก็ไม่ได้ยืมจากแถวที่อยู่ข้างบน รายการฝั่งเครือข่ายคือค่าธรรมเนียมพื้นฐาน 5000 lamport ต่อหนึ่งลายเซ็น ซึ่งเอกสารค่าธรรมเนียมของ Solana เองอธิบายที่มาไว้ครบ
| รายการ | โหมด SOL | โหมดโทเคน |
|---|---|---|
| ค่าธรรมเนียมแพลตฟอร์ม | 0.001 SOL | 0.001 SOL |
| ค่าธรรมเนียมเครือข่าย | 0.000005 SOL | 0.000005 SOL |
| บัญชีโทเคนของผู้รับ | ไม่เกี่ยวข้อง | 0.00203928 SOL และเฉพาะเมื่อผู้รับรายนั้นไม่เคยถือโทเคนตัวนี้มาก่อน |
แถวที่สามควรอ่านซ้ำอีกรอบ เพราะนี่คือรายการที่ทำให้คนสะดุด การส่งโทเคน SPL ไปยังที่อยู่ที่ไม่เคยแตะโทเคนตัวนั้นมาก่อน แปลว่าต้องสร้างบัญชีขึ้นมาใหม่เพื่อเก็บมัน และ Solana เก็บเงินมัดจำ rent สำหรับบัญชีนั้น เงินมัดจำก้อนนี้ราวสองร้อยเท่าของค่าธรรมเนียมเครือข่าย และเป็นสองเท่าของค่าธรรมเนียมแพลตฟอร์ม
ถ้ามีผู้รับหน้าใหม่หนึ่งร้อยราย รายการนี้จะกินบิลไปราว 0.204 SOL ในขณะที่ค่าธรรมเนียมแพลตฟอร์มหยุดอยู่ที่ 0.1 เงินมัดจำไม่ได้ถูกเผาทิ้ง มันค้างอยู่ในบัญชีโทเคนของผู้รับ และคืนให้กับใครก็ตามที่ปิดบัญชีนั้นในภายหลัง
แถวที่ถูกข้าม
ก่อนลงลายเซ็นจะมีการตรวจสองรอบ และทั้งสองรอบเลือกหยุดแถวนั้นไว้ แทนที่จะไปแก้ตัวเลขในแถว
รอบแรกเป็นเลขคณิตธรรมดา ถ้ากระเป๋าเงินผู้ส่งคลุมยอดของตัวเอง บวกค่าธรรมเนียม บวกบัญชีโทเคนที่อาจต้องเปิดใหม่ไม่ไหว แถวนั้นจะถูกทำเครื่องหมายไว้และปล่อยทิ้งไว้อย่างนั้น ไม่มีอะไรออกไปแบบครึ่ง ๆ กลาง ๆ
รอบที่สองแปลกกว่าและควรทำความเข้าใจไว้ เพราะครั้งแรกที่เจอมันดูเหมือนบั๊ก Solana ไม่ยอมให้เหลือบัญชีที่มียอดคงเหลือมากกว่าศูนย์ แต่ต่ำกว่าขั้นต่ำที่ได้รับยกเว้น rent สำหรับกระเป๋าเงินธรรมดา ขั้นต่ำนั้นคือ 0.00089088 SOL และตัวเลขนี้ออกมาจากสูตรในเอกสารเรื่องบัญชีของ Solana
การเทบัญชีให้ว่างสนิททำได้ การทิ้งไว้ 0.0005 SOL ทำไม่ได้ แถวที่ผลักกระเป๋าเงินเข้าไปอยู่ในช่องว่างนั้นจะถูกติดป้ายว่า rent dust และค้างอยู่โดยไม่ถูกส่ง
ทำไมไม่ตัดยอดลงมาให้พอดี
ทางเลือกอีกทางคือค่อย ๆ เฉือนยอดลงจนกว่าจะพอดี และทางนั้นแย่กว่า ตัวเลขนั้นคนกรอกเข้าไปเอง เครื่องมือที่ส่งตัวเลขอื่นออกไปเงียบ ๆ คือเครื่องมือที่หลังจากนั้นจะกระทบยอดกับตารางใบไหนก็ไม่ตรงอีกเลย
ให้ส่งยอดคงเหลือทั้งก้อนไปเลย หรือลดยอดลงจนส่วนที่เหลืออยู่เหนือขั้นต่ำ หน้าตัวอย่างบอกล่วงหน้าว่าแถวไหนโดนผลกระทบ และเครื่องมือจะถามหาบัญชีปลายทางทั้งหมดในการเรียกครั้งเดียวก่อนจะเซ็นอะไรทั้งสิ้น
หนึ่งธุรกรรมต่อหนึ่งแถว และทำไมเรื่องนี้ถึงสำคัญ
ในการโอนหลายกระเป๋าไปหลายกระเป๋า แต่ละแถวเป็นธุรกรรมของตัวเอง แถวที่ล้มจึงล้มอยู่แถวเดียว ถ้าเป็นชุดที่อัดทุกอย่างลงในธุรกรรมเดียว ความผิดพลาดที่แถวสามสิบจะลากยี่สิบเก้าแถวก่อนหน้าลงไปด้วย
เรื่องนี้มีราคาของมัน สี่สิบคู่แปลว่าลายเซ็นสี่สิบครั้ง และค่าธรรมเนียมแพลตฟอร์มสี่สิบครั้ง สิ่งที่ได้กลับมาคือผลลัพธ์ที่อ่านได้ทีละแถว ใครอยากรู้ว่าธุรกรรมพวกนี้เข้าเร็วแค่ไหน ตัวเลขอยู่ในบทความค่าธรรมเนียมลำดับความสำคัญ
เมื่อไรการโอนหลายกระเป๋าไปหลายกระเป๋าบน Solana คือรูปแบบที่ใช่
การหมุนกระเป๋าเงินคือคำตอบตรงไปตรงมาสำหรับคนส่วนใหญ่ มีกระเป๋าเงินชุดหนึ่งที่ติดประวัติซึ่งอยากทิ้งไว้ข้างหลัง จึงสร้างชุดใหม่ด้วยตัวสร้างกระเป๋าเงินจำนวนมาก แล้วอยากให้กระเป๋าเงินเก่าใบที่ 7 เติมเงินให้กระเป๋าเงินใหม่ใบที่ 7 เท่านั้น ไม่ใช่ใบอื่น
กรณีที่สองคือรายการจ่ายเงินที่ผู้จ่ายเปลี่ยนไปทีละแถว หลายโครงการ หลายกระเป๋าคลัง ตารางเดียว เครื่องมือส่งหลายรายการพูดแทนเรื่องนี้ไม่ได้เลย เพราะมันมีแหล่งเงินเพียงแหล่งเดียวเป๊ะ ๆ
กรณีที่สามคือการแบ่งใหม่หลังจากเก็บสแนปช็อต โดยผู้ถือแต่ละรายรับเงินจากกระเป๋าเงินที่กำหนดไว้ให้ล่วงหน้าแล้ว วิธีอ่านการกระจายตัวนั้นก่อนจะแบ่ง อยู่ในคู่มืออ่านการกระจายตัวของผู้ถือ
เตรียมรายชื่ออย่างไร
ให้รันรอบแรกของการโอนหลายกระเป๋าไปหลายกระเป๋าด้วยสองแถวก่อน ตารางผลลัพธ์จะบอกว่าหนึ่งแถวใช้เงินไปจริงเท่าไร รวมเงินมัดจำบัญชีโทเคนเข้าไปด้วย ก่อนจะยิงสองพันแถว
ตรวจด้วยว่าผู้รับถือโทเคนตัวนั้นอยู่แล้วหรือยัง ในรายชื่อที่ครึ่งหนึ่งเป็นผู้ถือเดิม รายการเงินมัดจำจะหายไปครึ่งหนึ่ง และที่ขนาดหนึ่งร้อยแถว รายการนี้คือตัวเลขที่ใหญ่ที่สุดในบิลทั้งใบ
จดไว้ก่อนเริ่มด้วยว่ากระเป๋าเงินใบไหนจ่ายแถวไหน หลังจากรันไปแล้ว การประกอบความสัมพันธ์นี้กลับคืนมายากกว่าที่ฟังตอนนี้ โดยเฉพาะเมื่อกระเป๋าเงินผู้ส่งเพิ่งถูกสร้างขึ้นมาสด ๆ และยังไม่มีประวัติอะไรให้แยกแยะออกจากกัน
เรื่องยอดคงเหลืออีกข้อสุดท้าย ให้เหลือเงินในกระเป๋าเงินผู้ส่งแต่ละใบมากกว่ายอดของมันสักหน่อย ถ้าเติมมาพอดีถึงทศนิยมตัวสุดท้าย การตรวจ rent จะเขี่ยแถวนั้นออกไป แล้วต้องกลับมาเติมเงินใหม่อีกรอบ ซึ่งช้ากว่าการเผื่อไว้ตั้งแต่แรก
อะไรเปลี่ยนไปเมื่อรายชื่อใหญ่ขึ้น
ที่สิบแถว ทุกอย่างข้างบนยังเป็นทฤษฎีที่สบาย ๆ พอถึงสองพันแถว มีสองเรื่องที่กลายเป็นงานจริง และทั้งสองเรื่องเกิดขึ้นนอกตัวเครื่องมือ
เรื่องแรกคือการเติมเงิน กระเป๋าเงินผู้ส่งทุกใบต้องมียอดของตัวเองบวกค่าธรรมเนียมพร้อมอยู่ก่อนเริ่ม และไม่มีทางที่แถวหนึ่งจะไปช่วยอุดอีกแถวหนึ่งได้ แปลว่าต้องมีรอบแจกจ่ายนำร่องหนึ่งรอบ ปกติออกจากกระเป๋าคลังใบเดียว และควรทำแบบเผื่อไว้มากกว่าคำนวณมาพอดีเป๊ะ
เรื่องที่สองคือการกระทบยอดหลังจบงาน ที่สี่สิบแถว มองตารางก็จบแล้ว ที่สองพันแถว จะอยากส่งออกผลลัพธ์แล้วเทียบกับไฟล์ต้นทางทีละแถว เพราะแถวที่ถูกข้ามจะไม่โผล่ในตัวสำรวจบล็อกเลยสักแถว มันไม่เคยมีตัวตนในฐานะธุรกรรม
ยังมีผลข้างเคียงข้อที่สามที่เห็นได้ยากกว่า ถ้าในรายชื่อมีทั้งผู้รับหน้าใหม่และผู้รับเดิมปนกัน ต้นทุนต่อแถวจะไม่คงที่ ค่าเฉลี่ยที่คำนวณจากสิบแถวแรกจะให้ตัวเลขที่ไม่เหมือนยอดรวมเลย ให้นับว่ามีผู้รับกี่รายที่ต้องเปิดบัญชีใหม่ แล้วคูณเฉพาะจำนวนนั้นด้วย 0.00203928 SOL
เรื่องที่มักถูกมองข้ามตอนวางแผน
คนที่ทำงานสายนี้บ่อย ๆ มักสะดุดเรื่องเดียวกันสองสามข้อ ข้อแรกคือการคิดว่าเครื่องมือจะช่วยหาเงินให้แถวที่ขาด มันไม่ทำ และเจตนาก็คือไม่ให้ทำ เพราะการหยิบเงินจากกระเป๋าเงินใบอื่นมาปิดแถวที่ขาด จะทำให้ความหมายของการจับคู่หายไปทันที
ข้อที่สองคือการวางแผนโดยดูแต่ยอดที่จะโอน แล้วลืมว่าค่าธรรมเนียมและเงินมัดจำก็ออกจากกระเป๋าเงินผู้ส่งใบเดียวกัน กระเป๋าเงินที่มีพอดีกับยอดโอนเป๊ะ ๆ จึงไม่พอเสมอ ส่วนต่างไม่มาก แต่มันเกิดกับทุกแถวพร้อมกัน
ข้อที่สามคือการอ่านผลลัพธ์ด้วยความคาดหวังผิด แถวที่ถูกข้ามไม่ใช่ธุรกรรมที่ล้มเหลว มันคือธุรกรรมที่ไม่เคยถูกสร้าง ถ้าไปตามหาในตัวสำรวจบล็อกจะไม่เจออะไรเลย และนั่นไม่ใช่สัญญาณว่ามีอะไรเสีย
คำถามที่พบบ่อยเกี่ยวกับการโอนแบบจับคู่
ต่างจากการรันเครื่องมือส่งหลายรายการหลายรอบอย่างไร?
เครื่องมือส่งหลายรายการมีแหล่งเงินหนึ่งแหล่งเป๊ะ ๆ ต่อการรันหนึ่งครั้ง สี่สิบแหล่งแปลว่ารันสี่สิบรอบ และสลับกระเป๋าเงินด้วยมืออีกสี่สิบครั้ง ที่นี่คือรันครั้งเดียวสี่สิบแถว
แถวที่ล้มมีค่าใช้จ่ายไหม?
ไม่มี แถวที่ผ่านการตรวจก่อนส่งไม่ได้จะไม่ถูกเซ็นเลย จึงไม่มีทั้งค่าธรรมเนียมเครือข่ายและค่าธรรมเนียมแพลตฟอร์ม
ผู้ส่งกับผู้รับซ้อนทับกันได้ไหม?
ได้ กระเป๋าเงินหนึ่งใบส่งในแถวหนึ่งและรับในอีกแถวหนึ่งได้ แต่ละแถวถูกตรวจแยกกัน
ทำไมแถวของฉันถูกติดป้ายว่า rent dust?
เพราะยอดที่เหลือในกระเป๋าเงินผู้ส่งจะตกอยู่ระหว่างศูนย์กับ 0.00089088 SOL ให้ส่งยอดทั้งก้อนไป หรือลดยอดลง
กระเป๋าเงินที่ส่งเฉพาะโทเคนต้องมี SOL ไหม?
ต้องมี ค่าธรรมเนียมเครือข่ายและค่าธรรมเนียมแพลตฟอร์มจ่ายด้วย SOL เสมอ ถึงแม้สิ่งที่ย้ายจะเป็นโทเคนก็ตาม
จำนวนคู่มีเพดานไหม?
ในทางปฏิบัติสิ่งที่จำกัดคือการเตรียมงาน ไม่ใช่ตัวเครื่องมือ กระเป๋าเงินผู้ส่งทุกใบต้องถูกเติมเงินไว้ล่วงหน้า
ตัดสินใจในบรรทัดเดียว
ถ้าตารางมีคอลัมน์ผู้จ่าย รูปแบบที่ต้องใช้คือการโอนหลายกระเป๋าไปหลายกระเป๋า ถ้าทุกแถวออกจากกระเป๋าเงินใบเดียวกัน ให้ใช้เครื่องมือส่งหลายรายการแล้วจ่ายครั้งเดียวแทนที่จะจ่ายสี่สิบครั้ง และถ้าแถวหายไปหนึ่งแถว ให้ดูขั้นต่ำของ rent ก่อนจะสรุปว่าเป็นบั๊ก เรื่องขั้นต่ำนี้มีต่อในคำอธิบายข้อผิดพลาดยอดไม่พอสำหรับ rent


