代码不能接受超过数组大小的文件?

Posted

技术标签:

【中文标题】代码不能接受超过数组大小的文件?【英文标题】:Code can't accept file that exceeds array size? 【发布时间】:2016-11-02 19:02:57 【问题描述】:

下面是我正在处理的项目的当前代码。它旨在获取学生及其成绩的文件,平均成绩,然后将它们全部放回输出文件中。学生人数不应超过 10 人,因此如果超过 10 名学生,则应仅阅读前 10 名,然后将顺序颠倒。当给定一个包含 10 多个学生的文件时,我的代码可以完美运行。它似乎正在尝试访问内存中不存在的部分。我试图让代码忽略空行,它应该这样做,但这似乎并没有解决它。我的“读取”功能是我认为问题所在。

#include <iostream>
#include <fstream>
#include <sstream>
#include <iomanip>

using namespace std;

//My student structure that holds the variable for each student object.
struct Student

    string fname;
    string lname;
    double average;
;

//Prototyping the functions to read the input file into an array and then reverse it.
int read(ifstream &fin, Student s[]);

void print(ofstream &fout, Student s[], int amount);

void reverse(Student s[], int amount);

int main()

    //Creating the file streams and global constant for the array and the filling it with I/O.
    const int size = 10;
    ifstream fin;
    ofstream fout;
    string inputFile;
    string outputFile;
    Student s[size];

    cout << "Enter input filename: ";
    cin >> inputFile;
    cout << "Enter output filename: ";
    cin >> outputFile;

    //opeining the files given by the user and then testing if the opened.
    fin.open(inputFile.c_str());
    fout.open(outputFile.c_str());

    if(fin.fail()) 
        cout << "Unable to open input file.\n";
        return 1;
    


    //calling my 3 functions and then returning to main(). Closing files as well.
    int count = read(fin , s);
    reverse(s, count);
    print(fout, s, count);
    count = 0;

    fin.close();
    fout.close();



//This function reads the file given and breaks it up using string stream. It then calculates the averages for each stuent and assigns it to the array.
int read(ifstream &fin, Student s[])

    istringstream sin;
    string line;
    string firstName;
    string lastName;
    double score;
    double total;
    double i=0;
    int totalStudents=0;
    Student stu;
    for(int j = 0; j < 10; j++)
    while(getline(fin, line))
        sin.clear();

        if(line.empty())
        
            j--;
        else
            sin.str(line);
        while(sin >> firstName >> lastName)
            stu.fname = firstName;
            stu.lname = lastName;

            while(sin >> score)
            total += score;
            i++;
            stu.average = (total/i);
            
        
        s[totalStudents]=stu;
        totalStudents++;
        stu.average = 0;
        total = 0;
        i = 0;

    
    
    

    //returning the number of students in the file so it can later be used for the variable of total students.
    return totalStudents;


//My print function that puts the array into a given output file.
void print(ofstream &fout, Student s[], int amount)

    for(int i = 0; i<amount; i++)
    
        if(s[i].lname.empty())
        
            fout<<"No students to report.";
        else
        ostringstream sout;
        sout << s[i].lname.c_str() << ", " << s[i].fname.c_str();
        fout <<setw(21)<< left << sout.str() << setprecision(2) << fixed << "= " << s[i].average << '\n';
    
    


//the function that reverses the order of the students by copying the last student into a temporary variable and casting it to the beggining.
void reverse(Student s[], int amount)

    Student temp;
    for(int i=0; i< amount/2; i++)
    

        temp=s[i];
        s[i]=s[amount-i-1];
        s[amount - i - 1] = temp;
    

【问题讨论】:

for(int j = 0; j &lt; 10; j++) while(getline(fin, line)) 看起来很可疑 调试器是解决此类问题的正确工具。 询问 Stack Overflow 之前,您应该逐行浏览您的代码。如需更多帮助,请阅读How to debug small programs (by Eric Lippert)。至少,您应该 [编辑] 您的问题以包含一个重现您的问题的 Minimal, Complete, and Verifiable 示例,以及您在调试器中所做的观察。 【参考方案1】:

在我看来,在找到空行后,您应该尝试使用 continue 语句,而不是:

for (int j = 0; j < 10; j++) 
    while (getline(fin, line)) 
        sin.clear();

        if (line.empty())
        
            continue;
        
        else 
            sin.str(line);
            while (sin >> firstName >> lastName) 
                stu.fname = firstName;
                stu.lname = lastName;

                while (sin >> score) 
                    total += score;
                    i++;
                    stu.average = (total / i);
                
            
            s[j] = stu;
            stu.average = 0;
            total = 0;
            i = 0;

        
    

根据 cmets,我错过了关于 for 循环的内容。它可以完全消除,只需要 while 循环和一个计数器:

int j = 0;
while (getline(fin, line) && j < 10)

    sin.clear();

    if (line.empty())
    
        continue;
    
    else
    
        sin.str(line);
        while (sin >> firstName >> lastName)
        
            stu.fname = firstName;
            stu.lname = lastName;

            while (sin >> score)
            
                total += score;
                i++;
                stu.average = (total / i);
            
        
        s[j] = stu;
        stu.average = 0;
        total = 0;
        i = 0;
        j++;
    

【讨论】:

可能无济于事。在以某种方式阅读学生之后,OP 仍然需要跳出内部 while 循环。 我认为我的问题可能与 totalStudents 变量有关。数组的最大大小为 10,但我认为 while 循环会尝试超过 10 的值,因为 totalStudents 不断增加。我不知道如何在不创建无限循环的情况下更改它。 @AndyG - 糟糕,我看的不够仔细。我添加了更好的代码,这应该会有所帮助。 非常感谢,我为总学生添加了一个计数器,并确保它小于 10,即限制。感谢您的帮助。

以上是关于代码不能接受超过数组大小的文件?的主要内容,如果未能解决你的问题,请参考以下文章

nodeJs巨大的数组处理抛出RangeError:超过最大调用堆栈大小

微信小程序如何查看是不是超过2m

数组大小超过函数大小 (C++)

IE8以上,用js获取上传文件大小和绝对路径的实现代码

我如何去创建任何我在代码后面定义大小的数组?

git添加文件个数超限制