Merging Two Files using C++

C

ckoniecny

I have the following two files:
File1:
11 John Doe
33 Jane Doe
55 Steve Smith

File2:
22 Joe Doe
44 Willy Widget

I'm trying to merge the two files to look like:

Output:
11 John Doe
22 Joe doe
33 Jane Doe
44 Willy Widget
55 Steve Smith

Note: I cannot use array's to sort.

This is the code I have thus far:

Code:
#include <iostream>
#include <fstream>
#include <string>

using namespace std;

int main()
{
ifstream File1, File2;
string File1_FirstName, File1_LastName;
string File2_FirstName, File2_LastName;
int File1_num, File2_num, NumberOne, NumberTwo;
ofstream outFile;

File1.open("File1.txt", ios::in);
File2.open("File2.txt", ios::in);

outFile.open("Output.txt", ios::eek:ut);



while (!File2.eof())
{
File1 >> File1_num >> File1_FirstName >> File1_LastName;
NumberOne = File1_num;

File2 >> File2_num >> File2_FirstName >> File2_LastName;
while (!File1.eof())
{
File1 >> File1_num >> File1_FirstName >> File1_LastName;
NumberTwo = File1_num;

if ( NumberOne > File2_num < NumberTwo )
{
outFile << NumberOne << '\t'
<< FirstName << '\t'
<< LastName << '\n';
}
}
}
return 0;
}
My output is not what I expected, I'm having logic issues. Can anyone
point me in the correct direction?
 
J

Jerry Coffin

I have the following two files:
File1:
11 John Doe
33 Jane Doe
55 Steve Smith

File2:
22 Joe Doe
44 Willy Widget

I'm trying to merge the two files to look like:

Output:
11 John Doe
22 Joe doe
33 Jane Doe
44 Willy Widget
55 Steve Smith

I'd define a class that holds the data and defines operator< to sort the
data in the desired fashion (you haven't described what should happen
if, for example, the same number appears with two different names).

From there, you can directly merge from input files to an output file if
the input files are guaranteed to be sorted, as you've shown them here.
Otherwise, you can copy from the input files to a sorted container (e.g.
set or multiset, depending on whether duplicate keys are allowed) and
then merge from there to the output.

I'm not sure why can _can't_ use arrays (as you mentioned in a snipped
portion of your post) but I'd certainly consider it ill-advised.

As far as the code you have goes, something like this:
while (!File2.eof())
{
File1 >> File1_num >> File1_FirstName >> File1_LastName;

is essentially certain to be incorrect, and normally needs to be
rewritten to something like:

while (file1>>input1>>input2>>input3>>inputN)
// whatever

The important point is that you need to check for a problem with reading
the input file AS you read it -- file.eof() only becomes true AFTER
you've reached the end of the file, so your loop attempts to read the
last data in the file twice. I'd forget about using explicit loops,
however, and just use an std::istream_iterator to read the input.

Your code also has a problem in that each iteration through the loop
reads input from each file, but only writes an output from one file --
and discards the input it read from the other file. Each iteration
should read only ONE input, to replace the one just written out.

As previously noted, however, I'd use std::merge() for this job -- it's
written specifically for tasks like this, and does them quite nicely.

class record {
int number;
std::string first_name, last_name;
public:
friend
std::istream &operator>>(std::istream &in, record &r) {
return in >> r.number >> r.first_name >> r.last_name;
}

friend std::eek:stream &operator<<(std::eek:stream &os, record const &r) {
return os << r.number << "\t"
<< r.first_name << "\t"
<< r.last_name;
}

bool operator<(record const &other) const {
return number < other.number;
}
};


// ...
std::merge(
std::istream_iterator<record>(infile1),
std::istream_iterator<record>(),
std::istream_iterator<record>(infile2),
std::istream_iterator<record>(),
std::eek:stream_iterator<record>(outfile, "\n"));
 
C

ckoniecny

Thats a little bit above my level. Is there anyway I can email you
what I have so you can see my actual program?
 
J

Jerry Coffin

Thats a little bit above my level. Is there anyway I can email you
what I have so you can see my actual program?

I do have email of course, but if you want help, it's generally better
to post here. That way 1) other people can chip in, and 2) other people
can learn from the discussion.
 
C

ckoniecny

This is what I have so far and its still not working.... Any hints?

#include <iostream>
#include <fstream>

using namespace std;

int main()
{
ifstream File1;
ifstream File2;
ofstream outFile;

string File1_fName, File1_lName;
string File2_fName, File2_lName;
int File1_acctNum, File2_acctNum;

File1.open("file1", ios::in);
File2.open("file2", ios::in);
outFile.open("out.txt", ios::eek:ut);

File1 >> File1_acctNum >> File1_fName >> File1_lName;
File2 >> File2_acctNum >> File2_fName >> File2_lName;
while (!File1.eof() && !File2.eof())
{
if (File2_acctNum > File1_acctNum)
{
outFile << File1_acctNum << '\t' << File1_fName
<< '\t'
<< File1_lName << " *\n";
outFile << File2_acctNum << '\t' << File2_fName
<< '\t'
<< File2_lName << " *\n";
File1 >> File1_acctNum >> File1_fName >>
File1_lName;
File2 >> File2_acctNum >> File2_fName >>
File2_lName;
cout << File2_acctNum << "\t" << File2_fName <<
"\t" << File2_lName << endl;
}
else if (File1.eof())
{
while (!File2.eof())
{
outFile << File2_acctNum << '\t' <<
File2_fName << '\t'
<< File2_lName << '\n';
}
}
else if (File2.eof())
{
while(!File1.eof())
{
outFile << File1_acctNum << '\t' <<
File1_fName << '\t'
<< File1_lName << '\n';
}
}

}
return 0;
}
 
J

Jerry Coffin

This is what I have so far and its still not working.... Any hints?

Not any new ones, really.
while (!File1.eof() && !File2.eof())

As already noted, code like this is almost always wrong. You want to
check for EOF _as_ you read the data.

I'd also split things up into a couple of functions, such as
"copy_remainder" (or something like that) to copy the remainder of a
file to the output.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,755
Messages
2,569,536
Members
45,013
Latest member
KatriceSwa

Latest Threads

Top