0

I need to read integers from a text file into a two-dimensional array.

-1 indicates the end of array. Every array supposes to have 6 positive integers (-1 does NOT count as part of the array).

For example, if my text file contains the following integers:

1 3 4 6 1 7 -1 1 3 5 7 2 3 -1 2 5 7 2 6 3 -1

That means when these integers are read into the program, there will be 3 arrays:

1st Array: 1 3 4 6 1 7

2nd Array: 1 3 5 7 2 3

3rd Array: 2 5 7 2 6 3

I wrote a program to assess if each array has a correct length (6 integers) AND correct integers (all integers should be positive) and output corresponding error messages if these criteria are not met.

#include <iostream>
#include  <fstream>
#include <string>
#define MAX_ROWS  3
#define MAX_COLUMNS 2

using namespace std;

int main()
{
    string fileName = "testdata.txt";                                                           //declare a string to store the Input File's name 
    ifstream inFile;                                                                             //name the input file connection 
    inFile.open(fileName);                                                                       //open the Input File
    string errorMessage = "Input file cannot be found";                                           //Declare a string to store an error message, just in case the Input file doesn't exist or cannot be found

    if (!inFile) {                                                                               //If the Input File doesn't not exist, then display the error message
        cout << errorMessage << '\n';                                                           //also store the error message to the Output file
        system("pause");
        return  0;                                                                               //end the program if the Input File does not exist
    }


    int checkNbr;
    int ArrB[MAX_ROWS][MAX_COLUMNS];
    int size = MAX_ROWS * MAX_COLUMNS;
    bool bad = false;
    bool invalidnum = false;

while (!inFile.eof())      
    {
        for (int i = 0; i < MAX_ROWS;i++) {
            for (int j = 0; j < MAX_COLUMNS; j++) {
                inFile >> ArrB[i][j];
                if (ArrB[i][j] == -1) {
                    bad = true;
                    cout << "\nThe array does not have enough integers" << endl;
                    break;
                    //return 1;
                }
                else {
                    if (ArrB[i][j] < 1) {
                        invalidnum = true;
                    }
                }
                cout << *(*(ArrB + i) + j) << " ";

            }
        }

        if (invalidnum == true) {
            invalidnum = false;
            cout << "\nThere is/are negative number(s) or zero(s) in the array imported from your text file.\n";
        }

        if (bad == false) {
            inFile >> checkNbr;
            if (checkNbr == -1) {
                cout << "\nThe size of the array is correct." << endl;
            }
            else {

                while (checkNbr != -1)
                {
                    cout << checkNbr;
                    cout << " ";
                    inFile >> checkNbr;

                }

                cout << "\nYou have too many numbers in this array\n";
            }
        }
    }

    return 0;
}

If I run my program:

Case 1 - PASSED

1 2 3 4 5 6 -1 3 5 2 1 6 8 3 2 5 -1 3 3 5 6 7 5 -1

enter image description here

Case 2 – PASSED

1 2 3 4 5 -6 -1 3 -5 2 1 6 8 -1 3 5 6 7 5 -1

enter image description here

Case 3 – FAILED(!)

1 2 3 4 -1 1 2 3 4 5 6 7 8 -1 1 2 3 4 5 -1

enter image description here

As you can see, case 3 failed. The second array (1 2 3 4 5 6 7 8) is actually longer than the declared array size, but it’s printing out “The array does not have enough integers” error message…..

The ONLY time this program won't work is when the first array does not have enough integers.

Any comments or hints would be appreciated!

EmmaG
  • 177
  • 8
  • 2
    Not your immediate problem, but `while (!inFile.eof())` is [a potential bug](https://stackoverflow.com/questions/5605125/why-is-iostreameof-inside-a-loop-condition-i-e-while-stream-eof-cons). – user4581301 Feb 21 '20 at 20:00
  • 2
    I recommend hammering this into a [mcve]. The more people have to change in order to make the program run, the more likely they are to accidentally fix the problem or introduce and debug a new one. If you do the MRE right, you'll probably find the bug yourself in the process. – user4581301 Feb 21 '20 at 20:07
  • Regarding `cout << *(*(ArrB + i) + j) << " ";`, why not `cout << ArrB[i][j] << " ";`? – user4581301 Feb 21 '20 at 20:14
  • @user4581301 yeah, either way works, so I didn't bother to change that part – EmmaG Feb 21 '20 at 20:17
  • Your ArrB isn't big enough to handle all the elements in case 3. – Jeffrey Jordan Feb 21 '20 at 20:20
  • @JeffreyJordan the bounds on `i` and `j` should prevent that. But... about that `break`... `break` is only a get out of jail card for one loop. A bug if not the bug. – user4581301 Feb 21 '20 at 20:23
  • @JeffreyJordan But the second array in my case 1 worked. The only time this program won't work is when the first array does not enough (6) integers.. – EmmaG Feb 21 '20 at 20:25
  • Step through this with a debugger and keep an eye on the value of `bad`. – user4581301 Feb 21 '20 at 20:27
  • I think half of your problem is that these messages should probably all be within the same If else block. – Andrew Ebert Feb 21 '20 at 20:30
  • @user4581301 I think there is something wrong with my break statement too, but I don't want my program to break out of the entire loop even if the first array does not have enough integers. In this case, where should I put my break at? – EmmaG Feb 21 '20 at 20:37
  • @AndrewEbert no...I don't think that would work. Because I am assessing my arrays based on two criteria. An criteria can met one of them, all of them, or none of them. – EmmaG Feb 21 '20 at 20:42
  • If you don't break out of both `for` loops you'll write data into the wrong spot in the array. This would be a good place for a function. The two `for` loops go in the function and `return` to exit both loops. – user4581301 Feb 21 '20 at 20:44
  • 2
    Another thing you could do is read out all of the numbers into vectors and then utilize the length of those vectors to determine if there are enough values. – Andrew Ebert Feb 21 '20 at 20:47

1 Answers1

1

The problem

bad is not reset after processing it.

Solution

Move bool bad = false; into the while (!inFile.eof()) loop body so it gets reset every iteration. If you define variables with the narrowest possible scope you can usually avoid this problem, so you should strongly consider doing the same thing with the rest of your variables.

This will solve the bug that was asked about and at least one other bug you haven't found yet. This leaves at least two more outstanding bugs for you to resolve, and both have been covered in the question's comments.

TL;DR version

A quick walk through of input 1 2 3 4 -1 1 2 3 4 5 6 7 8 -1 1 2 3 4 5 -1

1 2 3 4 -1 is parsed and found to be bad, so bad is set to true and the testing for a too-long value and clean-up is skipped. The file hasn't ended, so the program loops and starts reading the next array.

input remaining:

 1 2 3 4 5 6 7 8 -1 1 2 3 4 5 -1

output so far:

1 2 3 4 
The array does not have enough integers

1 2 3 4 5 6 is parsed. This fills the array and the for loops exit. bad is still true, so the check for overflow is skipped and no message is printed.

Input remaining:

 7 8 -1 1 2 3 4 5 -1

output so far:

1 2 3 4 
The array does not have enough integers
1 2 3 4 5 6

Now 7 8 -1 is parsed. This is too short to be an array and reported. Take careful note of what this does to the output.

Input remaining:

 1 2 3 4 5 -1

output so far:

1 2 3 4 
The array does not have enough integers
1 2 3 4 5 6 7 8 
The array does not have enough integers

Whoops. Looks like 1 2 3 4 5 6 7 8, not merely 7 8, was too short.

the program then parses 1 2 3 4 5 and finds it to be too short.

Input remaining:


output so far:

1 2 3 4 
The array does not have enough integers
1 2 3 4 5 6 7 8 
The array does not have enough integers
1 2 3 4 5 
The array does not have enough integers
Community
  • 1
  • 1
user4581301
  • 29,019
  • 5
  • 26
  • 45
  • Thank you so much for the detailed explanation!! This really helped me to understand exactly what was going on! Thank you! – EmmaG Feb 21 '20 at 21:27