2016-09-27 10 views
5

मेरे पास चेक जीसीसी और क्लैंग है और दोनों कोई चेतावनी उत्पन्न नहीं करते हैं। मुझे लगता है कि foo() से अस्थायी जीवनकाल पूर्ण अभिव्यक्ति के अंत तक लंबे समय तक बढ़ाया जाएगा, जहां बार फ़ंक्शन कॉल में अर्धविराम स्थित है।क्या यह कोड यूबी का कारण बनता है?

#include <iostream> 
#include <string> 

struct A 
{ 
    std::string foo() const{ return "aaa"; } 
}; 

void bar(const char* c) { 
    std::cout << c; 
} 

int main() 
{ 
    A a; 
    bar(a.foo().c_str()); // Is this safe? 
    bar(a.foo().substr().c_str()); // or this 
} 
+0

हाँ, तुम सही हो, यह सुरक्षित है –

उत्तर

7
अस्थायी foo() (और substr()) द्वारा दिया

bar कॉल (विधि कॉल की श्रृंखला के बाद) के अंत तक मौजूद रहेंगे, इस सुरक्षित है।

int main() 
{ 
    A a; 
    bar(a.foo().c_str()); 
    //temporary is destroyed here 
    bar(a.foo().substr().c_str()); 
    // and here 
} 

शास्त्रीय अपरिभाषित व्यवहार मामला:

int main() 
{ 
    A a; 
    const char* charPtr = a.foo().c_str(); 
    printf("%s", charPtr); 
} 

अस्थाई std::string बनाई गई है, यह करने के लिए एक सूचक है बफर c_str() द्वारा दिया जाता है और अस्थायी क्षेत्र से बाहर चला जाता है और नष्ट हो जाता है। charPtr अब एक अमान्य स्थान (एक मृत std::string) पर इंगित करने वाला सूचक है।

+0

यूबी उदाहरण बिल्कुल सही नहीं है। charPtr तब तक वैध रहता है जब तक एक गैर-कॉन्स ऑपरेशन को कॉल नहीं किया जाता है। – Trevir

+0

@Trevir 'printf' इसे मुद्रित करने के लिए इसका उपयोग करने का प्रयास कर रहा है बस पर्याप्त होना चाहिए। –

+0

printf ऑब्जेक्ट के साथ कैसे अंतर करता है? – Trevir

2
bar(a.foo().c_str()); 
bar(a.foo().substr().c_str()); 

संक्षिप्त उत्तर - हाँ, दोनों सुरक्षित हैं।

जो आप देख रहे हैं वह रावल्यू है।

एक rvalue (तथाकथित, ऐतिहासिक, क्योंकि rvalues ​​एक काम अभिव्यक्ति की दाएँ हाथ की ओर पर दिखाई दे सकता है) एक XValue, एक अस्थायी वस्तु या उसके subobject, या कि एक साथ संबद्ध नहीं है एक मूल्य है वस्तु।

और अधिक पढ़ें: What are rvalues, lvalues, xvalues, glvalues, and prvalues?

+1

यह एक रैवल्यू वास्तव में बिंदु –

+0

नहीं है? c_str() एक पॉइंटर को एक रावल्यू ऑब्जेक्ट में देता है। तो यह थोड़े मायने रखता है। यदि आप इस सूचक को बचाते हैं, तो यह खतरनाक है! –

संबंधित मुद्दे