2013-01-28 49 views
5

तो मैं डबल और लिंक्ड सूची में पहले और अंतिम नाम जोड़ने की कोशिश कर रहा हूं। मेरे पास "स्ट्रिंग, स्ट्रिंग" प्रारूप के साथ अलग-अलग लंबाई की विभिन्न टेक्स्ट फ़ाइलें हैं, और मैं अपने डेटा को स्टोर करने के लिए सूची का उपयोग कर रहा हूं।सूचियों और जोड़ों के बारे में भ्रम

मैं इस कोड का उपयोग कर रहा हूँ:

typedef std::list< std::pair<string,string> > listPair; 

...

list<pair<string, string> > mylist; 
ifstream myFile; 
myFile.open("20.txt"); 

pair<string, string> stuff; 
while (myFile >> stuff.first >> stuff.second) 
{ 
    mylist.push_back(stuff); 
} 

listPair::iterator iter = mylist.begin(); 

for(;iter != mylist.end();iter++) 
{ 
    string s = (*iter).first; 
    cout << s << endl; 
    string c = (*iter).second; 
    cout << c << endl; 
} 

अब समस्या मैं आ रही हैं कि सबसे पहले, सूची में अंतिम आइटम नहीं जोड़ा जा रहा है। प्रत्येक फ़ाइल की तरह ही अंत रेखा को याद करता है, इसलिए यह थोड़ा उलझन में है।

भी, मैं यह सुनिश्चित करने के लिए "mylist.size()" कर रहा हूं कि सभी नाम जोड़े गए हैं, और यह मुझे भ्रमित कर रहा है क्योंकि 99 नाम वाले टेक्स्ट फ़ाइल के लिए कहें, यानी 99 पंक्तियों की टेक्स्ट, यह कहेंगे (यह नहीं भूल रहा कि यह केवल अंतिम पंक्ति को खोने के कारण 98 में पढ़ता है) कि सूची का आकार 48 है।

क्यों 48? क्या ऐसा कुछ है क्योंकि मैंने जोड़े किए हैं, जो अभी भी समझ में नहीं आएंगे जैसे कि यह जोड़ों में नहीं पढ़ रहा था, वास्तव में इसके बारे में दोगुना हो जाएगा, क्योंकि जोड़े केवल पहले और अंतिम नाम को एक मान के रूप में लेते हैं।

मेरे लिए दिमागी दबदबा।

एक बार फिर आपकी सभी मदद के लिए धन्यवाद!

+0

शायद आप 'getline' की तलाश में हैं? –

+2

एक साइड नोट के रूप में, एक सामान्य उद्देश्य कंटेनर के रूप में आपको 'सूची' के बजाय 'वेक्टर' का उपयोग करना चाहिए। जिस तरह से आप इसका उपयोग कर रहे हैं, मुझे यहां 'सूची' की आवश्यकता दिखाई नहीं दे रही है। –

+0

क्या आप इनपुट फ़ाइल '20.txt' (या कम से कम एक निकास) जोड़ सकते हैं? शायद आपका इनपुट ठीक से प्रारूपित नहीं है। – Zeta

उत्तर

5

मैं एक अपनी फ़ाइल महसूस कर के रूप में आप का वर्णन किया है वास्तव में मानों के बीच रिक्तियां नहीं करता है, तो यह इस तरह दिखता है:

one,two 
three,four 
five,six 
seven,eight 
nine,ten 

आप इस पर अपने कार्यक्रम चलाने के लिए थे, तो आकार list का 2 (floor(number_of_lines/2) होगा, जो आपके लिए 48 देगा) और अंतिम पंक्ति list में बिल्कुल नहीं रखी जाएगी। क्यूं कर?

सबसे पहले, std::ifstream::operator>>(std::string&) पर प्रत्येक कॉल कुछ सफेद स्थान हिट होने तक निकाला जाएगा। इस मामले में, पहली पंक्ति पर पहली सफेद जगह \n इसके अंत में है। तो पहले पुनरावृत्ति पर, stuff.first"one,two" होगा और फिर अगली पंक्ति stuff.second में पढ़ी जाएगी, जिससे इसे "three,four" बना दिया जाएगा। इसके बाद इसे list में धकेल दिया जाता है। अगली दो पंक्तियां उसी तरह पढ़ी जाती हैं, जो आपको {"five,six","seven,eight"} जोड़ती हैं। अगले पुनरावृत्ति पर, पहले operator>>"nine,ten" निकालेंगे और दूसरा असफल हो जाएगा, जिससे while स्थिति समाप्त हो जाएगी और अंतिम पंक्ति को त्याग दिया जाएगा।

यदि आपके पास रिक्त स्थान हैं, तो भी आप के first में अल्पविराम के साथ समाप्त हो जाएंगे, जो निश्चित रूप से आप नहीं चाहते हैं।

एक समस्या के रूप में उपयुक्त है कि रेखा के दृष्टिकोण को यह std::getline उपयोग करने के लिए एक लाइन को निकालने के लिए है की तरह है, और फिर पार्स अच्छे रास्ता:

std::string line; 
std::pair<std::string, std::string> line_pair; 
while (std::getline(myFile, line)) { 
    std::stringstream line_stream(line); 
    std::getline(line_stream, line_pair.first, ','); 
    std::getline(line_stream, line_pair.second); 
    mylist.push_back(line_pair); 
} 

मैं भी जब तक आप का उपयोग करने के लिए एक अच्छा कारण है std::vector उपयोग करने की अनुशंसा std::list

+0

धन्यवाद, यह बिल्कुल मेरी समस्या है और यह पूरी तरह से काम किया! भगवान हर दिन हाहा सीखते हैं –

-1

ऑपरेटर > > ifstream पर अभी तक एक और टोकन के रूप में नई लाइन का इलाज करता है। इसलिए यह संभवतः आपकी पहली पंक्ति से सामान्य के अनुसार आपका पहला और दूसरा शब्द पढ़ेगा, लेकिन तीसरी टोकन पढ़ी पहली पंक्ति पर नई पंक्ति है।

न्यूलाइन के 'खाने' के लिए गेटलाइन का उपयोग करने का प्रयास करें।

+3

निकालने वाले किसी भी अन्य सफेद स्थान की तरह नई लाइनों का इलाज करते हैं। यदि आप लगातार 'ऑपरेटर >>' का उपयोग करते हैं तो आपको उनके चारों ओर छोड़ना नहीं है। –