व्यवहार में Quantisation
Quantisation हर weight को कम bits में स्टोर करता है ताकि मॉडल को कम मेमोरी की ज़रूरत पड़े। एक छोटे numpy उदाहरण के साथ ठीक से समझें कि 8-bit और 4-bit का क्या मतलब है।
60 सेकंड में
व्यवहार में Quantisation
Quantisation हर weight को कम bits में स्टोर करता है ताकि मॉडल को कम मेमोरी की ज़रूरत पड़े। एक छोटे numpy उदाहरण के साथ ठीक से समझें कि 8-bit और 4-bit का क्या मतलब है।
8-bit और 4-bit का असल में क्या मतलब है
| फ़ॉर्मैट | यह कितने अलग-अलग मान स्टोर कर सकता है | 16-bit के मुकाबले मेमोरी |
|---|---|---|
| 16-bit | 65,536 | 1× |
| 8-bit integer (int8) | 256 | लगभग ½ |
| 4-bit | 16 | लगभग ¼ |
- 1
रेंज खोजें
weights के एक समूह को देखें और सबसे बड़ा absolute मान खोजें। - 2
एक scale चुनें
int8 के लिए, scale = सबसे बड़ा मान ÷ 127, ताकि सबसे बड़ा weight 127 पर मैप हो जाए। - 3
Round करें
हर weight को scale से भाग दें, निकटतम पूर्ण संख्या में round करें, और इसे int8 के रूप में स्टोर करें। - 4
ज़रूरत पड़ने पर dequantise करें
मूल मान के करीब का मान पाने के लिए वापस scale से गुणा करें।
एक छोटा उदाहरण जिसे आप चला सकते हैं
import numpy as np
x = np.array([0.82, -1.37, 0.05, 2.41, -0.66, 0.0, 1.10, -2.02], dtype=np.float32)
# 1. One scale for the whole array: the largest value maps to 127
scale = np.abs(x).max() / 127
# 2. Quantise: divide, round, clip to the int8 range, store as int8
q = np.clip(np.round(x / scale), -127, 127).astype(np.int8)
# 3. Dequantise: multiply back by the scale
x_back = q.astype(np.float32) * scale
print("scale :", round(float(scale), 5))
print("int8 :", q)
print("restored :", np.round(x_back, 3))
print("max error :", float(np.abs(x - x_back).max()))
print("bytes : float32 =", x.nbytes, "| int8 =", q.nbytes, "+ one scale")Outliers से नुकसान क्यों होता है, और blocks से मदद क्यों मिलती है
क्वालिटी बनाम साइज़
- 8-bit कई मॉडलों और कार्यों के लिए अक्सर मूल के बहुत करीब होता है।
- 4-bit बहुत अधिक मेमोरी बचाता है और लैपटॉप व फ़ोन के लिए लोकप्रिय है, जिसमें क्वालिटी में थोड़ी ज़्यादा लेकिन अक्सर स्वीकार्य गिरावट आती है।
- 4 bits से नीचे, क्वालिटी अक्सर तेज़ी से गिरती है। छोटे मॉडल बड़े मॉडलों की तुलना में ज़्यादा संवेदनशील हो सकते हैं।
- आपके काम के लिए एकमात्र भरोसेमंद जवाब आपका अपना टेस्ट सेट है, जिसे हर वर्शन पर चलाकर देखा जाए।
- सबसे छोटी फ़ाइल चुनना क्योंकि यह तेज़ी से डाउनलोड होती है
- दो या तीन चैट सवालों से क्वालिटी की जांच करना
- 16-bit पर किसी दूसरे मॉडल से 4-bit मॉडल की तुलना करना
- सबसे कम bits चुनना जो अभी भी आपके टेस्ट सेट को पास कर लें
- अपने वास्तविक काम पर, अपने यूज़र्स की भाषाओं में टेस्ट करना
- एक ही टेस्ट पर अलग-अलग precisions वाले एक ही मॉडल की तुलना करना
और देखें और पढ़ें
लैब
numpy में आपका अपना int8 और 4-bit quantiser, मापी गई त्रुटियों (errors) और एक outlier प्रयोग के साथ।
समस्या
- शुरुआती कोड चलाएं। int8 की अधिकतम गड़बड़ी नोट करें।
- एक 4-bit वर्शन जोड़ें: -7 से 7 की रेंज का उपयोग करें, ताकि scale सबसे बड़ा मान ÷ 7 हो। int8 के साथ इसकी अधिकतम गड़बड़ी की तुलना करें।
- array में एक outlier (उदाहरण के लिए 50.0) जोड़ें। दोनों गड़बड़ियों को फिर से रिकॉर्ड करें। छोटे मानों के साथ क्या हुआ?
- अब 4 मानों के blocks में quantise करें, हर ब्लॉक का अपना scale हो। गड़बड़ियों को फिर से रिकॉर्ड करें। आपने क्या सीखा, इस पर तीन वाक्य लिखें।
प्रैक्टिस लैब
कोड में बदलाव करें और इसे रन करें। Python आपके ब्राउज़र में चलता है — हमारे सर्वर पर कुछ नहीं भेजा जाता।
कोई आउटपुट नहीं। वैल्यूज़ देखने के लिए print(...) जोड़ें।
आपका काम तब पूरा होगा जब
कठिन सवाल
उत्तर देखने से पहले ख़ुद जवाब देने की कोशिश करें। अगर आप इनके जवाब दे सकते हैं, तो आप पाठ समझ गए हैं।
Q1अपने स्वयं के scales वाले blocks गड़बड़ी को कम करते हैं। तो हर ब्लॉक को सिर्फ़ एक मान का लंबा क्यों न बना दिया जाए?दिखाएं
हर ब्लॉक को अपने scale की ज़रूरत होती है, और scale भी मेमोरी लेता है, अक्सर खुद मान से भी ज़्यादा bits। प्रति ब्लॉक एक मान के साथ आप हर weight के लिए एक पूरा scale स्टोर करेंगे और कुछ भी नहीं बचा पाएंगे। वास्तविक फ़ॉर्मैट एक ऐसा ब्लॉक साइज़ चुनते हैं जो scales के लिए लगने वाली अतिरिक्त मेमोरी के साथ सटीकता का संतुलन बनाए रखता है।
Q2किसी मॉडल को 4-bit में quantise करने से यह 16-bit की तुलना में लगभग चार गुना छोटा हो जाता है। generation अक्सर सिर्फ़ छोटा ही नहीं, बल्कि तेज़ भी क्यों होता है?दिखाएं
जब कोई मॉडल टेक्स्ट जनरेट करता है, तो उसे हर नए token के लिए मेमोरी से अपने weights पढ़ने होते हैं। अक्सर चिप गणित की गणना उतनी तेज़ी से कर सकती है जितनी तेज़ी से मेमोरी नंबर डिलीवर नहीं कर पाती। छोटे weights का मतलब है कम डेटा को मूव करना, इसलिए हर token जल्दी तैयार हो सकता है। यह कितना तेज़ होगा, यह हार्डवेयर और रनटाइम पर निर्भर करता है।
अक्सर पूछे जाने वाले सवाल
क्या quantisation मॉडल की जानकारी को बदल देता है?
यह जानबूझकर तथ्यों को नहीं हटाता है, लेकिन rounding हर weight में छोटी-छोटी गड़बड़ियां जोड़ देती है। अधिकांश समय जवाब समान रहते हैं। कभी-कभी, विशेष रूप से बहुत कम bits पर, जवाब ऐसे तरीकों से खराब हो जाते हैं जिनका अंदाज़ा लगाना मुश्किल होता है।
क्या मैं खुद किसी मॉडल को quantise कर सकता हूँ?
हाँ। llama.cpp में मॉडलों को GGUF में बदलने और quantise करने के टूल्स शामिल हैं, और अन्य फ़ॉर्मैट के लिए Python लाइब्रेरीज़ हैं। कई पब्लिशर और कम्युनिटी मेंबर्स पहले से तैयार quantised फ़ाइलें भी शेयर करते हैं, लेकिन यह जांच लें कि सोर्स भरोसेमंद हो।
क्या 4-bit हमेशा 8-bit से तेज़ होता है?
अक्सर होता है, क्योंकि मेमोरी से कम डेटा को मूव करना पड़ता है। लेकिन यह हार्डवेयर और रनटाइम पर निर्भर करता है। कुछ चिप्स में कुछ खास फ़ॉर्मैट के लिए तेज़ सपोर्ट होता है और दूसरों के लिए नहीं। अपनी खुद की मशीन पर माप कर देखें।
-128 के बजाय -127 पर clip क्यों करें?
int8 -128 को स्टोर कर सकता है, लेकिन -127 से 127 का उपयोग करने से दोनों तरफ रेंज समान रहती है, इसलिए पॉजिटिव और नेगेटिव मानों के साथ समान व्यवहार होता है। यह एक सामान्य और सरल चुनाव है, अकेला नहीं।
पाठ का टेस्ट
5 सवाल। पास होने और इस पाठ को पूरा करने के लिए 3 सही होने चाहिए (60%)।