Piraba
Piraba

Reputation: 7014

C++ combine two files output

I am new to C/C++ .I have 2 text files and need to combine two files contents

I executed like this g++ merge.cc -o merge and created two text files with content like this:

file1 : 1 3 5 7
file2 : 2 4 6 8

then excuted this command : ./merge 10 t1.txt t2.txt Out came : 1 2 3 4 5 6 7 81 2 3 4 5 6 7 8

#include <iostream>
#include <fstream>
#include <cstdlib>
using namespace std;

void combine(char s[], char t[], char result[]);

int main(int argc, char* argv[])
{      
    const int MAX = 20;
    char inBuffer1[MAX];
    char inBuffer2[MAX];
    char outBuffer[MAX*2];

    int max = atoi(argv[1]);
    ifstream file1(argv[2]);
    ifstream file2(argv[3]);

    file1.getline(inBuffer1,max);
    file2.getline(inBuffer2,max);

    combine (inBuffer1, inBuffer2, outBuffer);
    cout << outBuffer << endl;
}


void combine(char s[], char t[], char result[])
{
    int i, j, k;

    for (i = j = k = 0; s[i] && t[j]; k++)
    {
        if (s[i] <= t[j])
            result[k] = s[i++];
        else
            result[k] = t[j++];
        cout << result[k];
    }

    //tidy up
    for (; s[i]; )
    {
        result[k] = s[i++];
        cout << result[k++];
    }
    for (; t[j]; )
    {
        result[k] = t[j++];
        cout << result[k++];
    }
    result[k] = 0;
}

Could you please anyone explain about this. I thave to sort files and reserve output using -c, -r commands

Thanks in advance

Upvotes: 0

Views: 1456

Answers (3)

VolAnd
VolAnd

Reputation: 6407

The following C++ example shows usage of istream_iterator and ostream_iterator with merge method:

#include <iostream>
#include <fstream>
#include <algorithm>
#include <iterator>
using namespace std;

int main(int argc, char* argv[])
{      
    // open input files
    ifstream file1(argv[1]);
    ifstream file2(argv[2]);
    // link input streams with files
    istream_iterator<int> it1(file1);
    istream_iterator<int> it2(file2);
    istream_iterator<int> eos;  // end-of-stream iterator

    // link output stream to standard output
    ostream_iterator<int> oit (cout," "); // " " = usage of space as separator

    // marging to output stream
    merge(it1, eos, it2, eos, oit);

    file1.close();
    file2.close();
    return 0;
}

Upvotes: 0

VolAnd
VolAnd

Reputation: 6407

Try the following C-program example (without combine function):

#include <stdio.h>
#include <stdlib.h>

// compare function to sort int values
int comparator(const void *p, const void *q) 
{
    int l = *(int*)p;
    int r = *(int*)q; 
    return (l - r);
}

int main(int argc, char* argv[])
{      
    const int MAX = 20;
    int buffer[MAX*2];
    int cnt = 0; // numbers in buffer
    // check arguments
    if( argc < 3)
    {
        printf("Provide correct arguments: one number and two files with numbers\n");
        return 1;
    }

    // reading from 2 files in series
    FILE * f;
    for(int i = 2; i <= 3; i++)
    {
        f = fopen(argv[i], "r");
        if( f == NULL )
        {
            printf("File %s cannot be read!\n", argv[2]);
            break;
        }
        while( !feof(f) && cnt < MAX*2 ) // while file is not finished and array is not full
        {
            if( fscanf(f, "%d", &buffer[cnt]) ) // read data
                cnt++; // and if reading is successful count
        }
        fclose(f);
    }

    // sort the resulting array (instead of combine function)
    qsort(buffer, cnt , sizeof(int), comparator);

    // printing results
    for( int i = 0; i < cnt; i++)
    {
        printf("%d ", buffer[i]);
    }
}

This example is for cases when initial files can consist not ordered values, so all values from both files are read to memory and then sorted by standard function from stdlib.h (to use that qsort we need function comparator, read more in the references).

But for case when both input files are already arranged (sorted) program can be simpler, but you need open both files and compare values while reading to output the smallest value from two "current", and you do not need buffer array for that case (it is just a tip, try to write a program yourself).

EDIT:

It is C++ example with merge and sort from <algorithm>:

#include <iostream>
#include <fstream>
#include <algorithm>
#include <functional>
#include <vector>
using namespace std;

int main(int argc, char* argv[])
{      
    int data; // buffer to read one value from file
    ifstream file1(argv[1]);
    ifstream file2(argv[2]);
    vector<int> v1, v2; // vectors to store data

    // reading initial data to vectors
    while( !file1.eof() )
    {
        file1 >> data;
        v1.push_back(data);
    }
    file1.close();
    while( !file2.eof() )
    {
        file2 >> data;
        v2.push_back(data);
    }
    file2.close();
    // sorting  (essential if files are not sorted)
    sort(v1.begin(), v1.end(), less <int>());
    sort(v2.begin(), v2.end(), less <int>());
    // marging
    vector<int> res(v1.size() + v2.size()); // vector to store result
    merge(v1.begin(), v1.end(), v2.begin(), v2.end(), res.begin(), less <int>());

    // printing result
    for(vector<int>::iterator i = res.begin(); i != res.end(); i++)
    {
        cout << *i << " ";
    }
}

NOTE: In this example you do not need to ask user about size of data sequence, so argv[1] is name of the first file, and argv[2] is name of the second one (add appropriate check by yourself).

Upvotes: 1

Jerry Coffin
Jerry Coffin

Reputation: 490128

The c++ standard library has std::merge to do exactly what you seem to want here. Basically open the files, then do the merge from a couple of istream_iterators to an ostream_iterator.

Upvotes: 3

Related Questions