जैसा कि अन्य लोगों ने कहा है, मुद्दा सरणी में मेमोरी स्थान के लिए स्टोर है: x[i][j]
:। यहाँ अंतर्दृष्टि का एक सा क्यों है:
आपके पास 2-आयामी सरणी है, लेकिन कंप्यूटर में मेमोरी स्वाभाविक रूप से 1-आयामी है। तो जब आप इस तरह से अपने सरणी की कल्पना करते हैं:
0,0 | 0,1 | 0,2 | 0,3
----+-----+-----+----
1,0 | 1,1 | 1,2 | 1,3
----+-----+-----+----
2,0 | 2,1 | 2,2 | 2,3
आपका कंप्यूटर इसे एक पंक्ति के रूप में मेमोरी में संग्रहीत करता है:
0,0 | 0,1 | 0,2 | 0,3 | 1,0 | 1,1 | 1,2 | 1,3 | 2,0 | 2,1 | 2,2 | 2,3
दूसरे उदाहरण में, आप पहले नंबर पर लूपिंग द्वारा सरणी का उपयोग करते हैं, अर्थात:
x[0][0]
x[0][1]
x[0][2]
x[0][3]
x[1][0] etc...
मतलब कि आप उन सभी को क्रम में मार रहे हैं। अब पहले संस्करण को देखें। आप कर रहे हैं:
x[0][0]
x[1][0]
x[2][0]
x[0][1]
x[1][1] etc...
जिस तरह से सी ने 2-डी सरणी को मेमोरी में रखा है, आप इसे सभी जगह कूदने के लिए कह रहे हैं। लेकिन अब किकर के लिए: यह मामला क्यों है? सभी मेमोरी एक्सेस समान हैं, है ना?
नहीं: कैश की वजह से। आपकी मेमोरी से डेटा सीपीयू में थोड़ा-सा हिस्सा (जिसे 'कैश लाइनें' कहा जाता है) में लाया जाता है, आमतौर पर 64 बाइट्स। यदि आपके पास 4-बाइट पूर्णांक हैं, तो इसका मतलब है कि आप एक साफ छोटे बंडल में लगातार 16 पूर्णांक प्राप्त कर रहे हैं। यह वास्तव में स्मृति के इन टुकड़ों को लाने के लिए काफी धीमा है; आपके CPU को लोड करने के लिए एकल कैश लाइन में लगने वाले समय में बहुत काम किया जा सकता है।
अब एक्सेस के क्रम को देखें: दूसरा उदाहरण (1) 16 इनट्स का एक हिस्सा है, (2) उन सभी को संशोधित करता है, (3) 4000 * 4000/16 बार दोहराता है। यह अच्छा और तेज है, और सीपीयू में हमेशा काम करने के लिए कुछ होता है।
पहला उदाहरण है (1) 16 इनट्स का एक हिस्सा पकड़ो, (2) उनमें से केवल एक को संशोधित करें, (3) 4000 या 4000 बार दोहराएं। यह स्मृति से "भ्रूण" की संख्या के 16 गुना की आवश्यकता है। आपके सीपीयू को वास्तव में उस मेमोरी के इंतजार में बैठे हुए समय बिताना होगा, और जब वह आपके आस-पास बैठा हो, तो मूल्यवान समय बर्बाद कर रहा हो।
महत्वपूर्ण लेख:
अब आपके पास इसका जवाब है, यहाँ एक दिलचस्प बात है: इसका कोई अंतर्निहित कारण नहीं है कि आपका दूसरा उदाहरण सबसे तेज़ होना है। उदाहरण के लिए, फोरट्रान में, पहला उदाहरण तेज और दूसरा धीमा होगा। ऐसा इसलिए है क्योंकि सी की तरह वैचारिक "पंक्तियों" में चीजों का विस्तार करने के बजाय, फोरट्रान "कॉलम" में फैलता है, अर्थात:
0,0 | 1,0 | 2,0 | 0,1 | 1,1 | 2,1 | 0,2 | 1,2 | 2,2 | 0,3 | 1,3 | 2,3
C के लेआउट को 'रो-मेजर' और फोरट्रान को 'कॉलम-प्रमुख' कहा जाता है। जैसा कि आप देख सकते हैं, यह जानना बहुत महत्वपूर्ण है कि क्या आपकी प्रोग्रामिंग भाषा पंक्ति-प्रमुख या स्तंभ-प्रमुख है! यहाँ अधिक जानकारी के लिए एक लिंक है: http://en.wikipedia.org/wiki/Row-major_order