分段故障读取文件

时间:2016-11-13 15:08:49

标签: c++ iostream

#include <iostream>
#include <vector>
#include <fstream>
using namespace std;

struct Point
{
    double x;
    double y;
};

istream& operator>>(istream& is, Point& p)
{
    char ch;
    if(is >> ch && ch != '(')
    {
        is.unget();
        is.clear(ios_base::failbit);
        return is;
    }

    char ch2;
    double x;
    double y;

    is >> x >> ch >> y >> ch2;
    if(!is || ch != ';' || ch2 != ')')
    {
        cerr << "Error: Bad record!\n";
        exit(1);
    }
    p.x = x;
    p.y = y; 
}

ostream& operator<<(ostream& os, const Point& p)
{
    return os << '(' << p.x 
    << ';' << p.y << ')' << endl;
}

int main()
{
    Point p;
    vector<Point> original_points;
    cout << "Please enter 3 points:\n";
    for(int i = 0; i < 3; ++i)
    {
        cin >> p;
        original_points.push_back(p);
    }

    cout << "\nYou've entered:\n";

    for(Point x : original_points)
        cout << x;

    ofstream ost{"mydata"};
    for(Point x : original_points)
        ost << x;
    ost.close();

    vector<Point> processed_points;
    ifstream ist{"mydata"};
    while(ist >> p)
        processed_points.push_back(p);
    ist.close();

    cout << "original_points: ";
    for(Point x : original_points)
        cout << x;

    cout << "processed_points: ";
    for(Point x : original_points)
        cout << x;

    if(original_points.size() != processed_points.size())
        cout << "Oops! Seems like something went wrong!\n";
    return 0;
}

调试后我发现错误是由这行代码引起的:

while(ist >> p)

这部分代码几乎100%从book:

复制
istream& operator>>(istream& is, Point& p)
{
    char ch;
    if(is >> ch && ch != '(')
    {
        is.unget();
        is.clear(ios_base::failbit);
        return is;
    }

    char ch2;
    double x;
    double y;

    is >> x >> ch >> y >> ch2;
    if(!is || ch != ';' || ch2 != ')')
    {
        cerr << "Error: Bad record!\n";
        exit(1);
    }
    p.x = x;
    p.y = y; 
}

Google和stackoverflow说这个错误是由于以错误的方式访问内存造成的。我正在检查这段代码一小时,我无法弄清楚导致问题的原因。我今天开始研究流,这是“编程 - 使用C ++的原理和实践(第二版)”第10章的练习。

P.S。对不起我的英语语法,这不是我的母语)

1 个答案:

答案 0 :(得分:0)

并非函数operator>>(istream& is, Point& p)中代码的所有分支都会导致返回最终值,因此我认为您在功能结束时忘记了返回值return is;

istream& operator>>(istream& is, Point& p)
{
    char ch;
    if(is >> ch && ch != '(')
    {
        is.unget();
        is.clear(ios_base::failbit);
        return is;
    }

    char ch2;
    double x;
    double y;

    is >> x >> ch >> y >> ch2;
    if(!is || ch != ';' || ch2 != ')')
    {
        cerr << "Error: Bad record!\n";
        exit(1);
    }
    p.x = x;
    p.y = y; 
    return is;
}