ifstream runtime error when attempting to save the data into array - c++

I'm having a problem when I try to read the external text file.
The displayed text is correct but when it comes to saving the data into an array, it seems to be wrong.
My input numbers are 4 2 8 0 2 3 0 4 0 5, but after looping through the array, a[i], only '48' appears.
#include <iostream>
#include <windows.h>
#include <fstream>
#include <string>
void begin ();
void Process (string);
using namespace std;
int main()
{
begin();
system("pause");
return 0;
}
void begin (void){
string file = "data.txt";
Process(file);
}
void Process (string file)
{
int i=0,ch, n = 0, temp, a[50];
ifstream infile;
infile.open(file.c_str());
The error seems to be caused from here.
if(infile.is_open())
{
cout << "File to be read: " << file << endl;
cout << "\n\n";
infile >> temp;
while(!infile.fail())
{
cout << temp << " ";
infile >> temp;
a[i] = temp;
i++;
n++;
}
cout << "\n\n";
cout << "This file has " << n << " numbers. \n\n";
}
else
cout << "The file isn't available! \n\n";
infile.close();
When I try to output the result, only 48 appears.
for (int z = 0; z < i; z++)
{
cout << a[i] << endl;
}
}
I'm new here. Please help. Thanks in advance.

Your display loop is using i instead of z to index into a (this should be a good lesson on why variable naming is important!) Change your display loop to this:
for (int z = 0; z < i; z++)
{
cout << a[z] << endl;
}
There are potentially more issues with your code, but this seems to be what is blocking you. Consider renaming i and a to more meaningful things. The time you will spend typing will always be dwarfed by the time you spend trying to understand what you meant.

Consider this loop
for (int z = 0; z < i; z++)
{
cout << a[i] << endl;
}
You always output one element a[i] instead of a[z]. Moreover element with index i was not assigned. The last assigned element is a[i-1].
Apart from this you do not save the first entered number in the array. You start to save entered data from the second number.
infile >> temp; // <== this value was not assigned to an element of the array
while(!infile.fail())
{
cout << temp << " ";
infile >> temp;
a[i] = temp;
Also this statement inside the loop
infile >> temp;
can result in error. So after that there is no sense to write
a[i] = temp;
because nothing was entered and in fact you will store the previous number in the next element.

Related

How to solve a while loop that suddenly terminates itself?

I have code to look for permutations which takes input from the user until the user is satisfied with the amount of input added.
However, when receiving more than 4x input, the code suddenly stuck/terminated itself. I've tried changing the array type to dynamic memory, but the result continues to be the same.
Strangely when I test this code using http://cpp.sh/, it runs normally. I think the problem is with my compiler (I used VS code and MinGW to compile and run it.) What do you think is wrong?
My code is below:
#include <iostream>
#include <string>
using namespace std;
int main() {
int KombAngka;
bool Lanjut = true;
int x = 0;
int *Angka = new int(x);
string YaTidak;
while(Lanjut) {
cout << "Number-" << x + 1 << ": ";
cin >> Angka[x];
LoopYaTidak:
cout << "Are the numbers enough?(y/n)?: ";
cin >> YaTidak;
if (YaTidak == "y") {
Lanjut = false;
}
else if (YaTidak == "n") {
Lanjut = true;
}
else {
cout << "Enter the correct answer!(y/n)" << endl;
goto LoopYaTidak;
}
x++;
}
cout << "All numbers: (";
for (int z = 0; z <= x - 2; z++) {
cout << Angka[z] << ", ";
}
cout << Angka[x - 1] << ")" << endl;
cout << "The number of combinations of numbers used: ";
cin >> KombAngka;
int JumlahAngka = x;
const int StopLoop = JumlahAngka - KombAngka;
for (int i = JumlahAngka - 1; i > StopLoop; i--) {
JumlahAngka = JumlahAngka * i;
}
cout << "The number of queue numbers consisting of " << KombAngka << " different numbers are " << JumlahAngka << endl;
system("pause");
return 0;
}
This line
int *Angka = new int(x);
creates an integer on the heap with a value held by x which here it is 0.
You are accessing memory which you should not, and as mentioned by #fredrik it may cause a buffer overflow.
If you want to create an array on the heap you should do
int *Angka = new int[x];
This creates an array (on heap) of size x.
But since you are using c++ it's better to use vectors, you can simply create a vector with
std::vector<int> Angka;
Vector will take care of memory allocation and all other stuff that you would have to handle if you were to create an array with new.

sort and show the number of digits

I want to my program can sort the inputted integer and compute the number of any integer that inputted and I don't know where should write the cout of c
example
a[9]={2,3,2,6,6,3,5,2,2}
the number of 2 is 4
the number of 3 is 2
the number of 6 is 2
.
.
please fix this code
int main()
{
cout << "please enter the number of digites :" << endl;
int n;
cin>>n;
int a[n];
cout<<"enter numbers :"<<endl;
for(int i=0;i<n;i++)
cin>>a[i];
int i,j;
for(i=0;i<n-1;i++)
{
for(j=0;j<n-i-1;j++)
if(a[j]>a[j+1])
{
int temp;
temp=a[j+1];
a[j+1]=a[j];
a[j]=temp;
}
}
int c;
for(int m=0;m<n;m++)
{
if(a[m]==a[m+1])
c++;
else
c=0;
}
return 0;
}
Read through my solution, I've commented the parts I've changed. I tidied it up a little.
To answer your question: you should print the output (frequency of an integer in array) before you reset the count variable to 1. This will work because we have sorted the array, and will not have to look ahead for more occurrences of the current number.
[EDIT] I also added this above your code:
#include <iostream>
#include <vector>
using namspace std;
Full Solution
#include <iostream>
#include <vector>
using namespace std;
int main() {
// Get input
int n;
cout << "Please enter the number of digits: ";
cin>>n;
vector<int> a;
cout << "Enter " << n << " numbers: " << endl;
for(int i=0;i<n;i++) {
int temp;
cin >> temp;
a.push_back(temp);
}
// Sort input
int i,j;
for (i = 0; i < a.size(); i++) {
for(j = 0; j < a.size()-i-1; j++) {
if(a[j] > a[j+1]) {
int temp;
temp=a[j+1];
a[j+1]=a[j];
a[j]=temp;
}
}
}
// If an element is in an array
// we can not have 0 occurrences
// of that element, hence count
// must start at 1
int count = 1;
// Int to count
int current = a[0];
// Ouput if we have reset the count,
// or if it is the last iteration
bool output;
// Loop through array
for (int i = 1; i < a.size(); i++) {
output = false; // Reset output if we have printed
if (a[i] == current) {
// If current int and the element next to it are the same,
// increase the count
count++;
} else {
// If current and next are different,
// we need to show the frequency,
// and then reset count to 1
cout << current << " occurs " << count << " times" << endl;
count = 1;
current = a[i];
}
}
// Output one last time, for last int in sorted set
cout << current << " occurs " << count << " times" << endl;
return 0;
}
If this doesn't help, go and read this page, it is a solution in C, but can be adapted to C++ easily. https://codeforwin.org/2015/07/c-program-to-find-frequency-of-each-element-in-array.html This will help you understand and write the task. They take you step-by-step through the algorithm.
This is a typical use-case for a std::map. A std::map<char,int> lets you easily count the frequency of charaters (its easier to treat the user input as characters instead of converting it to numbers).
This is basically all you need:
#include <iostream>
#include <iterator>
#include <map>
int main(){
std::istream_iterator<char> it( std::cin );
std::istream_iterator<char> end_of_input;
std::map<char,int> data;
while (it != end_of_input ) data[*(it++)]++;
for (const auto& e : data) std::cout << e.first << " " << e.second << "\n";
}
This is probably a lot at once, so lets go one by one.
std::istream_iterator<char> lets you extract characters from a stream as if you are iterating a container. So the while iteratates std::cin until it reaches the end of the input. Then *(it++) increments the iterator and returns the character extracted from the stream. data[x]++ accesses the value in the map for the key x and increments its value. If there is no value in the map yet for the key, it gets default initialized to 0.
For input: 11223 it prints
1 2
2 2
3 1
Your code has some issues, not sure if I can catch them all...
You are using VLA (variable lenght arrays) here: int a[n];. This is a compiler extension and not standard c++.
You access the array out of bounds. When i == 0 then j goes up to j<n-i-1 == n-1 and then you access a[j+1] == a[n], but the last valid index into the array is n-1. Same problem in the other loop (a[m+1]).
Assuming your sorting works, the last loop almost gives you the number of elements, but not quite, to fix it you can change it to...
int current = a[0];
int counter = 1;
for(int m=1;m<n;m++) {
if(a[m] == current) {
counter++;
} else {
std::cout << current << " appears " << counter << " times" << endl;
counter=1; // note: minimum freq is 1 not 0
current = a[m];
}
}

Reading integers into an array C++

I'm trying to read a file called numbers.txt and insert the integers into an array. My code outputs only the last integer in the file.
//numbers.txt
1
10
7
23
9
3
12
5
2
32
6
42
My code:
int main(){
ifstream myReadFile;
myReadFile.open("/Users/simanshrestha/Dev/PriorityQueue/PriorityQueue/numbers.txt");
char output[100];
int count = 0;
if (myReadFile.is_open()) {
while (!myReadFile.eof()) {
myReadFile >> output;
//cout<< output << endl;
count++;
}
for(int i=0;i<count;i++)
{
cout << output[i];
}
cout<<endl;
}
cout << "Number of lines: " << count<< endl;
myReadFile.close();
return 0;
}
int main()
{
std::ifstream myReadFile;
myReadFile.open("/home/duoyi/numbers.txt");
char output[100];
int numbers[100];
int count = 0;
if (myReadFile.is_open())
{
while (myReadFile >> output && !myReadFile.eof())
{
numbers[count] = atoi(output);
count++;
}
for(int i = 0; i < count; i++)
{
cout << numbers[i] << endl;
}
}
cout << "Number of lines: " << count<< endl;
myReadFile.close();
return 0;
}
try this.
atoi is a function Convert a string to an integer.
you can try this also: same as the bottom
basically you need to define a "temp" or holder variable to store your data. and anything inside a loop stays in that loop cause of scope resolution, and overriding data each time you store it since it doesn't exit at all.
Hope this helps!
#include <fstream>
#include <iostream>
#include <cstdlib>
#include <string>
using namespace std;
const string FILE = "your file name here";
int main()
{
ifstream myReadFile;
myReadFile.open(FILE);
char output[100];
int numbers[100];
int count = 0;
if (myReadFile.is_open()){
while (myReadFile >> output && !myReadFile.eof()) //not stopping until we reach end of file
{
numbers[count] = atoi(output); //converts string to int
count++;
}
for(int i = 0; i < count; i++)
{
cout << numbers[i] << endl;
}
}
cout << "Number of lines: " << count+1 << endl; //total number of lines in file
myReadFile.close();
else{ cout << "Error: File name not loaded" << endl;}
return 0;
}
May I hazard a guess that your code is getting the sum of all the numbers and it is saved in the 1st element of your array?
May I also guess you want the number of the first line in the text file to be saved in the first element of the array? 2nd line in 2nd element so on and so forth?
If so, the following code might need updating:
myReadFile >> output;
to
myReadFile >> output[count];
I'm quite sure this will work in C and assume this would work in C++ too
updated:
another thing to add is to have 2D array like this:
char output[100][5]; //assuming our number is at most 5 char long

calculating a sum with two variables from user created output file

I'm trying to figure out how exactly I'd use my output text file I created to be used to calculate the sums of both variables. My output text file is saving the information correctly, but I get 0 and 0 for my sums so it's not reading the information I think. Also, does the information I enter into the arrays only save into the text file? I need it only being saved into the text file so that the sum calculations are only receiving information from the text file
#include <iostream>
#include <string>
#include<iomanip>
#include <fstream>
using namespace std;
int main() {
int ItemNumber[2];
float price[2];
int sumnumber = 0;
float sumprice = 0;
string myfile = "c:/Users/rz/Desktop/numbers.txt";
int count = 0;
ofstream outFile;
outFile.open(myfile);
while (count <= 1)
{
cout << "enter a price" << endl;
cin >> price[count];
outFile << price[count] << endl;
cout << "enter a item number" << endl;
cin >> ItemNumber[count];
outFile << ItemNumber[count] << endl;
count++;
}
outFile.close();
fstream inFile;
inFile.open(myfile);
while (count <= 1)
{
sumprice = sumprice + price[count];
sumnumber = sumnumber + ItemNumber[count];
}
cout << sumnumber << endl;
cout << sumprice << endl;
system("pause");
return 0;
}
At the end of the first loop:
int count = 0;
while (count <= 1) { ... count++ ... }
the variable count will be set to 2.
Then, when you start the second loop:
while (count <= 1) ...
the condition is already false, hence the body of the loop will never be executed.
In order for this to work, you would have to reset count back to zero so that it runs through the items again. Or, better yet, leave count alone (since it indicates how many items were processed) and use another variable to got through them:
for (int i = 0; i < count; ++i) { ... use i rather than count ... }

Trying to ask a user to provide a set of numbers, then have program determine if the numbers are in ascending order or not?

I am trying to create a program that asks the user for a set of numbers, first asking for the quantity of numbers, then having them input all the numbers. The program then checks the numbers, and determines whether or not the numbers given are in ascending order or not. Then, simply print out "yes ascending" or "no not ascending" and print out the array on one line..So far, my code will just always say that "yes, this is an increasing array!" Please look below for my code. Thanks in advance!..
tested: 1 2 3 4 5 6 --> pass
1 3 5 2 4 6 --> fail (still says it is an ascending array)
#include <iostream>
#include <string>
using namespace std;
bool isAscending(int arr[], int size)
{
for (int i=0; i < size-1; i++)
{
if (arr[i] > arr[i+1])
{
return false;
}
}
return true;
}
int main()
{
int arraysize = 0;
string numbers;
cout << "Enter the size of the array: " << endl;
cin >> arraysize;
if (arraysize < 1)
{
cout << "ERROR: you entered an incorrect value for the array size!" << endl;
}
cout << "Enter the numbers in the array, separated by a space, and press enter: " << endl;
numbers += ' ' + numbers;
cin >> numbers;
int arr[arraysize];
if ( isAscending(arr, arraysize))
{
cout << "This IS an increasing array!" << endl;
}
else
{
cout << "This is NOT an ascending array!" << endl;
}
for (i = 0; i < arraysize - 1; i++)
{
cout << arr[i];
}
return 0;
}
You're reading in "numbers", which you created as type String.
cout << "Enter the numbers in the array, separated by a space, and press enter: " << endl;
numbers += ' ' + numbers;
cin >> numbers;
Your numbers+= line isn't doing anything except adding a space to your numbers string before your cin happens... I know what you're trying to accomplish, and that won't do it.
Then you're suddenly making an array which, without initializing is filled with garbage, and immediately running isAscending on it:
int arr[arraysize];
if ( isAscending(arr, arraysize)){....}
I advise you declare your array before receiving input, read the input line and process it into INTEGERS, and then add each integer to your array. Here is a (crude) correction of the first section of code in your main that just reads in whitespace separated integers and fills the array with them:
int main(){
int arraysize = 0;
int number = 0;
cout << "Enter the size of the array: " << endl;
cin >> arraysize;
if (arraysize < 1) // you should really have this loop until you get correct input
{ cout << "ERROR: you entered an incorrect value for the array size!" << endl; }
int* arr = new int[arraysize];
cout << "Enter the numbers in the array, separated by a space, and press enter: " << endl;
int i = 0;
while(i < arraysize){
cin >> number;
arr[i] = number;
i++;
};
if ( isAscending(arr, arraysize)){ cout << "This IS an increasing array!" << endl; }
else{ cout << "This is NOT an ascending array!" << endl;}
for (int i = 0; i < arraysize; i++){
cout << arr[i];
if( (i+1) == arraysize){ cout << ". ";}
else cout << ", ";
}
return 0;
}
If you're going to whine about somebody giving partial answers that only address the asker's question, maybe you should take the time to write something yourself.