2011-02-17 12 views
5

मैं सी ++ में एक बुनियादी शिफ्ट सिफर लागू करने की कोशिश कर रहा हूं। मैं तब तक आगे नहीं बढ़ सकता जब तक कि मुझे पता न लगे कि सेगमेंटेशन गलती क्या हो रही है। मैंने जीडीबी का उपयोग कर कोड के माध्यम से कदम रखा और समस्या इटेटरेटर से निकलती प्रतीत होती है।इस स्ट्रिंग के माध्यम से पुनरावृत्ति करते समय मुझे सेगमेंटेशन गलती क्यों मिलती है?

1 #include <iostream> 
2 #include <string> 
3 
4 std::string encrypt (std::string plain, int key); 
5 
6 int main() 
7 { 
8   std::string plaintext; 
9   std::getline(std::cin,plaintext,'\n'); 
10  encrypt(plaintext,3); 
11 } 
12 
13 std::string encrypt(std::string plain, int key) 
14 { 
15   std::string::iterator ic; 
16   for (ic= plain.begin(); ic != plain.end();++ic) 
17   { 
18     std::cout <<*ic + key << std::endl; 
19   } 
20 } 

त्रुटि:

Program received signal SIGSEGV, Segmentation fault. 
0x00007ffff7b73ef1 in std::basic_string<char, std::char_traits<char>, std::allocator<char> >::~basic_string()() from /usr/lib/libstdc++.so.6 

उत्तर

8

आप एक std::string लौटने के रूप में encrypt घोषणा की है, लेकिन आप समारोह से कुछ भी वापस नहीं है। आपको एक मूल्य वापस करने की आवश्यकता है या आपको यह इंगित करने के लिए कि रिटर्न प्रकार कुछ भी वापस नहीं लौटाता है, आपको void होने के लिए रिटर्न प्रकार बदलने की आवश्यकता है।

के लिए क्यों लिखा गया है, मैं केवल अनुमान लगा सकता हूं। यह संभावना है कि ऑब्जेक्ट को encrypt रिटर्न को साफ करने के लिए main में std::string विनाशक को संकलक उत्पन्न हुआ है। चूंकि encrypt वास्तव में कुछ भी वापस नहीं करता है, इसलिए विनाशक उस वस्तु के लिए बुला रहा है जो अस्तित्व में नहीं है। स्मृति जिसमें वस्तु होनी चाहिए, में केवल कचरा डेटा होता है और विनाशक इसे पसंद नहीं करता है।

+0

लेकिन उसे '~ basic_string' में एसआईजी क्यों मिलता है? – osgx

+0

आह धन्यवाद यह तय किया गया है कि –

+0

मुझे यह भी पता नहीं था कि यह संकलित हो सकता है। जिस तरह से @ कर्नेल, सही जवाब स्वीकार करना न भूलें! – Marlon

1

समस्या यह है कि आपके encrypt फ़ंक्शन में return कथन का अभाव है।

फिक्सिंग कि, const के संदर्भ द्वारा तार गुजर,

std::string const& plain 

चीयर्स & hth।,

+0

और फिर मैं const_iterator का उपयोग करूंगा? या इससे कोई फर्क नहीं पड़ता? –

+1

@the_ कर्नेल: आपको 'const_iterator' का उपयोग करना चाहिए, हां। –

+0

ठीक है बहुत बहुत धन्यवाद। ये सभी सुझाव बहुत ही जानकारीपूर्ण/उपयोगी रहे हैं –

3

एक पाश लेखन की तरह मानते हैं, लेकिन इसे बदलने के लिए

return "blah blah"; 

इसके अलावा जोड़े एक इटरेटर का उपयोग करने के लिए एक इंडेक्स का उपयोग करने से आमतौर पर एक गलती होती है। यदि आप एक स्पष्ट लूप का उपयोग करने जा रहे हैं, तो आमतौर पर string जैसे कुछ के लिए, किसी भी इंडेक्स का उपयोग करना जारी रखने के लिए अधिक समझदारी होती है जो यादृच्छिक पहुंच की अनुमति देता है। इटरेटर्स का प्राथमिक बिंदु जेनेरिक एल्गोरिदम सक्षम करना है जो कंटेनर के साथ नहीं हैं। पुनरावर्तक का अच्छा इस्तेमाल करने के लिए, एक एल्गोरिथ्म के साथ उपयोग करें:

int main() { 
    std::string plaintext; 
    std::getline(std::cin, plaintext); 

    std::transform(plaintext.begin(), plaintext.end(), 
        std::ostream_iterator<char>(std::cout), 
        std::bind2nd(std::plus<int>(), 3)); 
    return 0; 
} 

संपादित करें: केवल अपेक्षाकृत

std::transform(line.begin(), line.end(), 
       std::ostream_iterator<char>(std::cout), 
       [](char ch) { return ch+'\03'; }); 

: चूंकि हंस Passant यह लाया, एक लैम्ब्डा अभिव्यक्ति का उपयोग कर एक संस्करण इस प्रकार दिखाई देगा जीसीसी> = 4.6, विजुअल स्टूडियो> = 2010.

+0

जो कि मैं जो करने की कोशिश कर रहा था उससे निश्चित रूप से अधिक सहज लगता है। धन्यवाद मैं एसटीएल एल्गोरिदम में अधिक देखूंगा –

+0

उस बिक्री के लिए लैम्ब्स का उपयोग करें। –

5

[C++2003 Standard section 6.6.3-2] Flowing off the end of a function is equivalent to a return with no value; this results in undefined behavior in a value-returning function.

यदि आपका संकलक आपको चेतावनी देता नहीं है बनाने के लिए एक बहुत ही आसान गलती है - हाल ही में compilers हालांकि इस समर्थन करते हैं। आप जितना संभव हो उतने कंपाइलर चेतावनियों को सक्षम करके स्वयं को बहुत अधिक डिबगिंग बचा सकते हैं। जीसीसी/जी ++ के मामले में, मैं आपके द्वारा लिखे गए किसी भी नए कोड के लिए "-Wall -Werror" के साथ संकलन करने का सुझाव देता हूं। उन विकल्पों के साथ, इस प्रोग्राम का संकलन निम्न संदेश के साथ विफल रहता है:

cc1plus: warnings being treated as errors 
In function 'std::string encrypt(std::string, int)': 
Line 20: warning: control reaches end of non-void function 
+0

जो निश्चित रूप से टिप के लिए जीवन को बहुत आसान बना देगा –

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