यहां ओपनसीएल कर्नेल से कोड के दो टुकड़े हैं जिन पर मैं काम कर रहा हूं; वे काफी अलग रन-टाइम प्रदर्शित करते हैं।ओपनसीएल: इन दो मामलों के बीच प्रदर्शन इतना अलग क्यों है?
कोड अपेक्षाकृत जटिल है, इसलिए मैंने इसे सरल बना दिया है।
इस संस्करण में एक सेकंड के तहत में चलता है:
for (int ii=0; ii<someNumber;ii++)
{
for (int jj=0; ii<someNumber2;jj++)
{
value1 = value2 + value3;
value1 = value1 * someFunction(a,b,c);
double nothing = value1;
}
}
और इस संस्करण को चलाने के लिए चारों ओर 38 सेकंड लेता है:
for (int ii=0; ii<someNumber;ii++)
{
for (int jj=0; ii<someNumber2;jj++)
{
value1 = value2 + value3;
value1 = value1 * someFunction(a,b,c);
}
double nothing = value1;
}
मैं कहता हूँ के रूप में, कोड (इस की तुलना में कुछ अधिक जटिल है वहाँ लूप में कई अन्य चीजें चल रही हैं), लेकिन परिवर्तनीय "कुछ नहीं" वास्तव में ब्रेस के तुरंत बाद तुरंत से आगे बढ़ता है।
मैं ओपनसीएल के लिए बहुत नया हूं, और मैं यह नहीं कर सकता कि क्या हो रहा है, इसे ठीक करने के लिए बहुत कम है। कहने की जरूरत नहीं है, धीमा मामला वास्तव में मेरे कार्यान्वयन में मुझे चाहिए। मैंने पता रिक्त स्थान के साथ गड़बड़ करने की कोशिश की है (यहां सभी चर __private में हैं)।
मैं केवल कल्पना कर सकता हूं कि कुछ कारणों से जीपीयू परिवर्तनीय "वैल्यू 1" को धीमा स्मृति में बंद कर रहा है जब ब्रेस बंद हो जाता है। क्या यह एक संभावित स्पष्टीकरण है? मैं क्या कर सकता हूँ?
अग्रिम धन्यवाद!
अद्यतन: यह एक सेकंड के भीतर भी चलता है: (लेकिन किसी भी लाइन को अपरिवर्तित करने के साथ, यह अत्यधिक धीमी गति से बदल जाता है)। यह लूप में कोई अन्य बदलाव किए बिना है, और वैल्यू 1 अभी भी उसी स्थान पर घोषित किया गया है जैसा कि पहले था।
for (int ii=0; ii<someNumber;ii++)
{
for (int jj=0; ii<someNumber2;jj++)
{
// value1 = value2 + value3;
// value1 = value1 * someFunction(a,b,c);
}
double nothing = value1;
}
अद्यतन 2: के रूप में दिखाया गया कोड वास्तव में value1
की घोषणा के साथ, इस तरह एक और पाश में नेस्ट किया गया था:
double value1=0;
for (int kk=0; kk<someNumber3;kk++)
{
for (int ii=0; ii<someNumber;ii++)
{
for (int jj=0; ii<someNumber2;jj++)
{
value1 = value2 + value3;
value1 = value1 * someFunction(a,b,c);
}
double nothing = value1;
}
}
बढ़ते जहां value1
यह भी घोषणा की हमें तेजी से मामले को वापस हो जाता है है:
for (int kk=0; kk<someNumber3;kk++)
{
double value1=0;
for (int ii=0; ii<someNumber;ii++)
{
for (int jj=0; ii<someNumber2;jj++)
{
value1 = value2 + value3;
value1 = value1 * someFunction(a,b,c);
}
double nothing = value1;
}
}
ऐसा लगता है कि ओपनसीएल एक बेहद मुश्किल कला है! मैं अभी भी वास्तव में समझ नहीं पा रहा हूं कि क्या हो रहा है, लेकिन कम से कम मुझे पता है कि इसे कैसे ठीक किया जाए!
यह बहुत अजीब है। क्या आप वाकई धीमे संस्करण का उपयोग करने की ज़रूरत है? इन स्निपेट से वे कार्यात्मक रूप से समान दिखते हैं। – Chriszuma
आपके उत्तर के लिए धन्यवाद। हाँ मुझे यकीन है, लेकिन आप सही हैं कि मैंने जो उदाहरण दिए हैं वे कार्यात्मक रूप से समान हैं। आंतरिक ब्रेसिज़ में कोड एक + = होना चाहिए। – carthurs
मुझे कोई कारण नहीं दिख रहा है कि दूसरे कोड को उन कोड स्निपेट के आधार पर धीमा होना चाहिए। मुझे लगता है कि असाइनमेंट को ले जाना कहीं साइड इफेक्ट्स होना चाहिए, जैसे बढ़ी हुई शाखाएं (एक कार्य इकाई 'if' निष्पादित करती है, अगला' अन्य 'निष्पादित करती है), जो वास्तव में GPU को धीमा कर सकती है। –