कृपया बताएं कि कोड के पहले स्निपेट का परिणाम -1 क्यों नहीं है।

    string s = "abc";
    int amount = -1;
    cout << "amount to shift before modulus: " << amount<<endl;
    amount %= s.size();
    cout << "mod " <<s.size()<<endl;
    cout << "amount to shift after modulus: " << amount<<endl;

आउटपुट:
मापांक से पहले शिफ्ट की जाने वाली राशि: -1
मॉड 3
मापांक के बाद शिफ्ट की जाने वाली राशि: 0

    string s = "abc";
    int sSize = s.size();
    int amount = -1;
    cout << "amount to shift before modulus: " << amount<<endl;
    amount %= sSize;
    cout << "mod " <<sSize<<endl;
    cout << "amount to shift after modulus: " << amount<<endl;

आउटपुट:
मापांक से पहले शिफ्ट की जाने वाली राशि: -1
मॉड 3
मापांक के बाद शिफ्ट की जाने वाली राशि: -1

मैं एक कोडिंग चुनौती को पूरा कर रहा था जब मुझे इस व्यवहार का सामना करना पड़ा और मुझे समझ में नहीं आया कि क्या हो रहा है। यह व्यवहार उत्पन्न नहीं होता है यदि राशि एक धनात्मक संख्या है जैसे कि 1.

1
Calamari 15 अप्रैल 2020, 04:50

1 उत्तर

सबसे बढ़िया उत्तर

यदि आप एक हस्ताक्षरित पूर्णांक और एक अहस्ताक्षरित पूर्णांक के बीच अंकगणित (अंकगणितीय तुलना सहित) करते हैं, और अहस्ताक्षरित पूर्णांक प्रकार कम से कम हस्ताक्षरित पूर्णांक जितना चौड़ा है, तो हस्ताक्षरित पूर्णांक एक अहस्ताक्षरित पूर्णांक में परिवर्तित हो जाता है . (यह तथाकथित "सामान्य अंकगणितीय रूपांतरण" का परिणाम है। )

इसके लगभग हमेशा अप्रत्याशित परिणाम होते हैं, जब तक कि अंकगणितीय संक्रिया जोड़ या घटाव न हो। कई मामलों में, यदि आप चेतावनियों का अनुरोध करते हैं, तो एक अच्छा संकलक आपको मिश्रित-चिह्न अंकगणित करने के बारे में चेतावनी देगा। (अत्यधिक अनुशंसित!) यह केवल एक अपेक्षाकृत असामान्य संस्करण है।

पहले मामले में, s.size() size_t प्रकार का है, जो एक अहस्ताक्षरित प्रकार है, संभवतः 64 बिट्स का; इसलिए, यह int से चौड़ा है। इसलिए amount % s.size() की गणना करने के लिए, कंपाइलर पहले amount को एक अहस्ताक्षरित size_t में बदल देता है, जिसके परिणामस्वरूप 264-1 हो जाएगा। जैसा कि होता है, वह संख्या 3 से विभाज्य है, इसलिए मोडुलो ऑपरेशन 0 देता है।

आपके दूसरे मामले में, आप s.size() को एक हस्ताक्षरित पूर्णांक में बदलने के लिए बाध्य करते हैं। चूंकि मान निश्चित रूप से int की सीमा के भीतर है, इसलिए रूपांतरण अच्छी तरह से परिभाषित है। बाद में मॉड्यूलो ऑपरेशन int s पर किया जाता है, जो हस्ताक्षरित होते हैं, और अपेक्षित परिणाम प्राप्त करते हैं यदि आप हस्ताक्षरित मॉड्यूलो को सी ++ में काम करने की अपेक्षा करते हैं। (देखें मॉड्यूलो का उपयोग करते समय C++ नेगेटिव नंबर क्यों आउटपुट करता है? अधिक जानकारी के लिए।)

4
rici 15 अप्रैल 2020, 02:25