2017-02-27 65 views
-1

我正在通過本書中的練習加速C++,並且在閱讀while循環中的字符串時遇到問題。該代碼似乎有點選擇該人的名字讀取多少。任何想法爲什麼這被切斷?我已經進入Xcode進行調試,看起來全名只是沒有被讀入。cin沒有閱讀完整字符串

代碼的想法是,你可以鍵入一個學生的名字,然後是期中考試,期末考試然後一系列作業成績來計算他們的最終成績。然後它會按字母順序返回名稱,並在其旁邊顯示最終標記,並將其格式化,以便最終標記位於單個列中。

GradeFinder.ccp(主)

#include <algorithm> 
#include <iomanip> 
#include <ios> 
#include <iostream> 
#include <stdexcept> 
#include <string> 
#include <vector> 
#include "grade.cpp" 


using std::cin; 
using std::cout; 
using std::endl; 
using std::domain_error; 
using std::max; 
using std::setprecision; 
using std::sort; 
using std::streamsize; 
using std::string; 
using std::vector; 

int main() 
{ 
    vector<Student_info> students; 
    Student_info record; 
    string::size_type maxlen=0; 

    while (read(cin,record)) 
    { 
    maxlen=max(maxlen,record.name.size()); 
    students.push_back(record); 
    } 

    sort(students.begin(),students.end(),compare); 

    for (vector<Student_info>::size_type i=0; i!=students.size();++i) 
    { 
    cout<<students[i].name 
     <<string(maxlen+1-students[i].name.size(),' '); 

     try 
     { 
     double final_grade=grade(students[i]); 
     streamsize prec=cout.precision(); 
     cout<<setprecision(3)<<final_grade 
      <<setprecision(prec); 
      } 
     catch (domain_error e) 
     { 
      cout<<e.what(); 
     } 
     cout<<endl; 
    } 
return 0; 
} 

'Student_info.h'

#ifndef GUARD_Student_info 
#define GUARD_Student_info 

// Student_info.h header file 
#include <iostream> 
#include <string> 
#include <vector> 

struct Student_info { 
    std::string name; 
    double midterm, final; 
    std::vector<double> homework; 
}; 

bool compare(const Student_info&, const Student_info&); 
std::istream& read(std::istream&, Student_info&); 
std::istream& read_hw(std::istream&, std::vector<double>&); 

#endif // GUARD_Student_info 

Student_info.cpp(讀取的名稱和相關的標記的命令行輸入)

#include "Student_info.h" 

using std::istream; 
using std::vector; 

bool compare(const Student_info& x, const Student_info& y) 
{ 
    return x.name<y.name; 
} 

istream& read(istream& is, Student_info& s) 
{ 
    is >> s.name >> s.midterm >> s.exam; 
    read_hw(is,s.homework); 
    return is; 
} 

istream& read_hw(istream& in, vector<double>& hw) 
{ 
    if (in) 
    { 
     hw.clear(); 

     double x; 
     while (in>>x) 
     hw.push_back(x);  
    in.clear(); 

    } 
    return in; 
}  

的以下是命令行輸入的一個例子,有趣的是這個名字當佩內洛普不是輸入的第一個名字時,會導致問題,而約翰尼總是很好。

Chapter4 Alex$ ./GradeFinder 
Johnny 90 90 90 90 90 
Frederick 80 80 80 80 80 
Penelope 85 85 85 85 85 
Polly 95 95 95 95 95 95 
Johnny 90 
lope  85 
olly  95 
rederick 80 

Chapter4 Alex$ ./GradeFinder 
Penelope 85 85 85 85 85 
Frederick 80 80 80 80 80 80 
Polly 95 95 95 95 95 95 
Johnny 90 90 90 90 90 90 
Johnny 90 
Penelope 85 
olly  95 
rederick 80 
+2

您正在使用'std :: istream :: operator >>'進行所有閱讀。 'operator >>'忽略換行符,並在遇到空格時停止讀取字符串。此外,在少數不包含任何考試或家庭作業分數的線上,您的閱讀將會失敗。所以你並不總是閱讀你所期望的。考慮首先使用'std :: getline()'將整行文本讀入'std :: string',然後根據需要使用'std :: istreamstream'從該行讀取單個值。 –

+0

編輯包含student_info.h,這是理解程序行爲的必要文件。完整的源代碼在這裏:https://github.com/acarabott/accelerated-cplusplus/tree/master/04 – Squirrel

+0

請考慮編輯你的問題只包含[mcve] ...它似乎只有2個函數實際上從istream中讀取,所以你可以明顯減少我們必須讀取的代碼數量。 – zett42

回答

0

看來問題是,使用libc++似乎吞某些字符(A,B,C,d,E,F,I,N,P,X),當他們出現在名稱的開始。

通過切換編譯爲libstdc++它不再刪除名稱中的字符。但是,我不知道如何解決這個問題,同時仍然使用libc++

請參閱here以獲取相同問題的答案。它似乎可能是一個Mac相關的問題。