C++ Read file into vectors - c++

I'm having trouble figuring out how to read a file line by line into different data type vectors. Is there a way to do this with inFile >> ? My code is below. Thanks in advance!
void fileOpen()
{
fstream inFile;
inFile.open(userFile);
// Check if file open successful -- if so, process
if (!inFile.is_open()) {cout << "File could not be opened.";}
else
{
cout << "File is open.\n";
string firstLine;
string line;
vector<char> printMethod;
vector<string> shirtColor;
vector<string> orderID;
vector<string> region;
vector<int> charCount;
vector<int> numMedium;
vector<int> numLarge;
vector<int> numXL;
getline(inFile, firstLine); // get column headings out of the way
cout << firstLine << endl << endl;
while(inFile.good()) // while we are not at the end of the file, process
{
while(getline(inFile, line)) // get each line of the file separately
{
for (int i = 1; i < 50; i++)
{
inFile >> date >> printMethod.at(i);
cout << date << printMethod.at(i) << endl;
}
}
}
}
}

Before you use vector.at(i) in your case you should be sure that your vector is long enough cause at will generate out of range exception. As I can see from your code your vector printMethod contains no more than 50 elements so you can resize vector printMethod before use e.g.
vector<char> printMethod(50);
or
vector<char> printMethod;
printMethod.resize(50);
If you're planning to use a variable number of elements more than 50 you should use push_back method like #Phil1970 recommended e.g.
char other_data;
inFile >> date >> other_data;
printMethod.push_back(other_data);

Related

How to read a file line by line and separate the lines components?

I am new to C++ (I usually use Java) and am trying to make a k-ary heap. I want to insert values from a file into the heap; however, I am at a loss with the code for the things I want to do.
I wanted to use .nextLine and .hasNextLine like I would in Java with a scanner, but I am not sure those are applicable to C++. Also, in the file the items are listed as such: "IN 890", "IN 9228", "EX", "IN 847", etc. The "IN" portion tells me to insert and the "EX" portion is for my extract_min. I don't know how to separate the string and integer in C++ so I can insert just the number though.
int main(){
BinaryMinHeap h;
string str ("IN");
string str ("EX");
int sum = 0;
int x;
ifstream inFile;
inFile.open("test.txt");
if (!inFile) {
cout << "Unable to open file";
exit(1); // terminate with error
}
while (inFile >> x) {
sum = sum + x;
if(str.find(nextLin) == true //if "IN" is in line)
{
h.insertKey(nextLin); //insert the number
}
else //if "EX" is in line perform extract min
}
inFile.close();
cout << "Sum = " << sum << endl;
}
The result should just add the number into the heap or extract the min.
Look at the various std::istream implementations - std::ifstream, std::istringstream, etc. You can call std::getline() in a loop to read a std::ifstream line by line, using std::istringstream to parse each line. For example:
int main() {
BinaryMinHeap h;
string line, item;
int x sum = 0;
ifstream inFile;
inFile.open("test.txt");
if (!inFile) {
cout << "Unable to open file";
return 1; // terminate with error
}
while (getline(inFile, line)) {
istringstream iss(line);
iss >> item;
if (item == "IN") {
iss >> x;
sum += x;
h.insertKey(x);
}
else if (item == "EX") {
// perform extract min
}
}
inFile.close();
cout << "Sum = " << sum << endl;
return 0;
}

How do I get an input file to read into a string array in C++?

For some reason the full lines from my input file are not reading into the array, only the first word in each line. I am currently using the getline call, but I am not sure why it is not working. Here is the what I have for the call to populate the array. The txt file is a list of songs.
const int numTracks = 25;
string tracks[numTracks];
int count = 0, results;
string track, END;
cout << "Reading SetList.txt into array" << endl;
ifstream inputFile;
inputFile.open("SetList.txt");
while (count < numTracks && inputFile >> tracks[count])
{
count++;
getline(inputFile, track);
}
inputFile.close();
while (count < numTracks && inputFile >> tracks[count])
The >> operator reads a single word. And this code reads this single word into the vector in question.
getline(inputFile, track);
True, you're using getline(). To read the rest of the line, after the initial word, into some unrelated variable called track. track appears to be a very bored std::string that, apparently, gets overwritten on every iteration of the loop, and is otherwise completely ignored.
Your loop is using the operator>> to read the file into the array. That operator reads one word at a time. You need to remove that operator completely and use std::getline() to fill the array, eg:
const int numTracks = 25;
std::string tracks[numTracks];
int count = 0;
std::cout << "Reading SetList.txt into array" << std::endl;
std::ifstream inputFile;
inputFile.open("SetList.txt");
while (count < numTracks)
{
if (!std::getline(inputFile, tracks[count])) break;
count++;
}
inputFile.close();
Or:
const int numTracks = 25;
std::string tracks[numTracks];
int count = 0;
std::cout << "Reading SetList.txt into array" << std::endl;
std::ifstream inputFile;
inputFile.open("SetList.txt");
while ((count < numTracks) && (std::getline(inputFile, tracks[count]))
{
count++;
}
inputFile.close();
Alternatively, consider using a std::vector instead of a fixed array, then you can use std::istream_iterator and std::back_inserter to get rid of the manual loop completely:
class line : public std::string {}
std::istream& operator>>(std::istream &is, line &l)
{
return std::getline(is, l);
}
...
std::vector<std::string> tracks;
std::cout << "Reading SetList.txt into array" << std::endl;
std::ifstream inputFile;
inputFile.open("SetList.txt");
std::copy(
std::istream_iterator<line>(inputFile),
std::istream_iterator<line>(),
std::back_inserter(tracks)
);
inputFile.close();

C++ Tokenize part of a String

Trying to tokenize a String in C++ which is read from a file, separated by commas, but I only need the first 3 data of every line.
For example:
The lines look like this:
140,152,2240,1,0,3:0:0:0:
156,72,2691,1,0,1:0:0:0:
356,72,3593,1,0,1:0:0:0:
But I only need the first 3 data of these lines. In this case:
140, 152, 2240156, 72, 2691356, 72, 3593
I'm trying to add these data into a vector I just don't know how to skip reading a line from the file after the first 3 data.
This is my current code: (canPrint is true by default)
ifstream ifs;
ifs.open("E:\\sample.txt");
if (!ifs)
cout << "Error reading file\n";
else
cout << "File loaded\n";
int numlines = 0;
int counter = 0;
string tmp;
while (getline(ifs, tmp))
{
//getline(ifs, tmp); // Saves the line in tmp.
if (canPrint)
{
//getline(ifs, tmp);
numlines++;
// cout << tmp << endl; // Prints our tmp.
vector<string> strings;
vector<customdata> datalist;
istringstream f(tmp);
string s;
while (getline(f, s, ',')) {
cout << s << " ";
strings.push_back(s);
}
cout << "\n";
}
How about checking the size of the vector first? Perhaps something like
while (strings.size() < 3 && getline(f, s, ',')) { ... }

c++ initializing array storage size

void start ( string fname )
{
string FirstElement;
int count = 0 ;
fstream Infile;
Infile.open( fname.c_str(), ios::in ); // Open the input file
while(!Infile.eof()) // using while to look for the total lines
{
count++;
}
//read to the array
string data_array[]; //initializing an array
for(int i=0; !Infile.eof(); i++){
Infile >> data_array[i]; // storing the value read from file to array
}
//Display the array
// for(int i=1; i<11; i++){
// cout << data_array[i] << endl;
//}
cout << data_array[0] << endl;
cout << count << endl;
return;
}
I have a text files contain values lines by lines
My plan was to use the while loop to do a total count of the lines
and place it in the "string data_array[]" but somehow it doesnt work that way.
anyone can advise me on how can I make it in a way that It can have a flexible storage size going according to the numbers of values in the text files? thanks
For flexible storage as you call it, you may use STL's container, such as std::vector<T> or std::list<T>. Other issues are highlighted in inline comments.
// pass by reference
void start(const std::string& fname)
{
// use std::ifstream, instead of std::fstream(..., std::ios::in);
std::ifstream Infile(fname.c_str());
// prefer std::vector to raw array
std::vector<std::string> data_array;
std::string line;
// read line by line
while (std::getline(Infile, line))
{
data_array.push_back(line); // store each line
}
// print out size
std::cout << data_array.size() << std::endl;
// display the array, note: indexing starts from 0 not 1 !
for(int i = 0; i < data_array.size(); ++i)
{
std::cout << data_array[i] << std::endl;
}
}

How to use any stream on wstring to extract data

I was reading data from a file using wifstream
the txt file looks like this:
1,2,3,4,5,6,7
2,3,4,5,6,7,8
...
...
each number is an id I needed for my program and comma is the separator
Here is my code
wifstream inputFile(FILE_PATH);
if(inputFile)
{
wchar_t regex;
int id;
while(inputFile)
{
inputFile>>id;
inputFile.get(regex);
cout << id << ", ";
}
inputFile.close();
}
This code works perfectly fine, until I change the reading scheme in which a single line is read at a time, I wanted to do something similar on the line so I can read data from the line while the buffer of the stream pops the data once it's been read like above. But I can't get it working.
Here is my code
wifstream inputFile(FILE_PATH);
wstring line;
if(inputFile)
{
while(!inputFile.eof())
{
std::getline(inputFile, line);
for(int i=0; i<line.length(); i+=2)
{
int id;
wchar_t regex;
wstringstream(line)>>id; // doesn't work as it keep getting the same number
wstringstream(line).get(regex);
cout << id << ", ";
}
cout << endl;
}
inputFile.close();
}
I think the reason it doesn't work is that I'm not using a stream properly and it keeps reading the id at the very first index and never progress no matter how many times I use >> (probably not the right way to use it anyways), I also tried wifstream, no use either.
How am I supposed to get around with this?
You are recreating the wstringstream each time you use it. Move the creation outside the loop:
wifstream inputFile(FILE_PATH);
wstring line;
if(inputFile)
{
while(!inputFile.eof())
{
std::getline(inputFile, line);
wstringstream istring(line);
for(int i=0; i<line.length(); i+=2)
{
int id;
wchar_t regex;
istring>>id;
istring.get(regex);
cout << id << ", ";
}
cout << endl;
}
inputFile.close();
}