2012-05-09 24 views
1

私は、fstream:カラムを使ってフォーマットされた出力を作ることを切望しています。フォーマットされた出力:カラム

は(関数FUNC1、FUNC2何でも)出力を生成する(同じファイル、 "example.dat" への書き込み)の二つの機能があります

#include <fstream> 

int main() 
{ 
    std::ofstream fout;  
    fout.open("example.dat"); 

    for (int i=0; i<10; i++) 
    { 
     fout << Func1(i) << std::endl; 
    }; 

    // Func2 depends on Func1, thus them **cannot** be written at the same time: 
    // fout << Func1() << " " << Func2() << std::endl; 

    for (int i=0; i<10; i++) 
    { 
     fout << Func2(i) << std::endl; 
    }; 

    return 0; 
} 

出力を意志に似て:

関数func1 (0)

Func1(1)

。 。

関数func1(9)

関数func2(0)

関数func2(1)

FUNC2(9)

私の質問は:

関数func1(0)FUNC2(0)

関数func1(1)FUNC2(1)

:2列として、この出力を生成する方法

これらは同時に書き込まれませんが。

私はseekp()、tellp()を使う必要があると思っていますが、残念ながら私はこれについて大きな専門家ではありません。

助けてください!

ありがとうございます。

+0

は、あなただけの2 'ベクトル'にはfunc1とfunc2の出力をバッファリングすることができませんか? – Benj

+0

ありがとうBenj、 – Pomeron

+1

タイトルから(C++)を削除するには、質問を編集する必要があります。あなたはC++タグを持っているなら、それを置く必要はありません。 – tinman

答えて

0

は、なぜあなたは

は(構文はおそらく間違っている)、これはstd ::ベクトルを使用seekpとtellp(およびファイルの真ん中への書き込みはどのような場合には不注意のために落とし穴がいっぱいです)必要があります:

std::vector<std::string> res1; 
std::vector<std::string> res2; 
res1.reserve(10); 
res2.reserve(10); 
for (std::size_t i = 0; i < 10; ++i) 
{ 
    std::stringstream s; 
    s << func1(i); 
    res1[i] = s.str(); 
} 
//same for res2, func2 
for (std::size_t i = 0; i < 10; ++i) 
{ 

    cout << res1[i] << " " << res2[i] << "\n"; 
} 

これはおそらくフォーマットが正しくないため、ビットを調整する必要があります。 std :: listがうまくいくかもしれません。

+0

BenjとTom Tannerに感謝します。コードabvoeはオリジナルコードのプロトタイプのみです。実際には、私は約100列あり、長さはそれぞれ50^4です。それらのすべてを記憶に残しておくとおそらくそれを殺すでしょう。したがって、私はそれを自分の.datファイルに書き込んで、メモリを解放してもう一度実行することに興味があります(データの次の部分)。 – Pomeron

0

あなたが実際にそれらをメモリに保持できないと仮定すると、2つのファイルに書き込むことができます。先頭に戻り、行単位で読み込み、最後のファイルに出力して連結カラムを作成します。

このような何かがうまくいくかもしれない(私はそれをテストしていませんでした):

#include <fstream> 
#include <string> 
int main() 
{ 
    std::fstream fs_func1; 
    std::fstream fs_func2; 
    std::ofstream fout; 

    fs_func1.open("func1.dat") 
    for (int i=0;i<10;i++) 
    { 
     fs_func1 << Func1(i) << std::endl; 
    } 
    fs_func1.seekg(0); // Set get pointer to start of file 

    fs_func2.open("func2.dat"); 
    for (int i=0;i<10;i++) 
    { 
     fs_func2 << Func2(i) << std::endl; 
    }; 
    fs_func2.seekg(0); // Set get pointer to start of file 

    fout.open("example.dat"); 
    while (!fs_func1.eof() && !fs_func2.eof()) 
    { 
     std::string func1_line; 
     std::string func2_line; 

     std::getline(fs_func1, func1_line); 
     std::getline(fs_func2, func2_line); 

     fout << func1_line << " " << func2_line << std::endl; 
    } 

    return 0; 
} 

ワンステップであなたのためにこれを行うだろうUnixコマンドラインツールは、おそらくあります。

+0

おかげでtinman!しかし、私の場合、連結された列は徐々に現れるはずです。巨大なデータファイルを扱うので、読み書きは時間がかかります。したがって、私はメインファイル "example.dat"を保存(オープン)し、各実行のたびに新しい列を追加する必要があります。あなたは非常に素晴らしいソリューションを提供しましたが、インクリメンタルに変更する方法はありますか? – Pomeron

+0

@Pomeron:forループを小さなセクションに分割できない限り、コードをインクリメンタルに簡単に変更できるとは思いません。 0〜9の場合はFunc1()、0〜9の場合はFunc2()、10〜19の場合はFunc1()を呼び出します。変更することはできますが、全く異なるものになります。 – tinman

-1
for (int i=0;i<10;i++) 
{ 
    fout << Func1(i); 
}; 
fout<<endl; 

for (int i=0;i<10;i++) 
{ 
    fout << Func2(i); 
}; 
fout<<endl; 
+0

私はdownvoterではありませんが、2つの列ではなく、2つの列に出力を生成します。あなたがそれを2つの列に転記する方法を示すために答えを変更すると、それはおそらく良い答えになるでしょう。 – tinman

0
vector<ostringstream> streams(10); 

for (int i=0; i < 10; ++i) 
{ 
    streams[i] << Func1(i); 
} 

for (int i=0; i < 10; ++i) 
{ 
    streams[i] << " " << Func2(i); 
} 

ofstream fout("example.dat"); 

for (int i=0; i < 10; ++i) 
{ 
    fout << streams[i].str() << endl; 
} 
+0

ニースのソリューション!しかし、それは〜600 MBまでベクトルに格納することができますか? – Pomeron

+0

私は100個の "for"ループを持っており、各ループは〜6-7MBの.datファイルを生成します。だから、あなたのソリューションを使うためには、私は100X(6-7MB)の情報を保存しなければなりません。 "ベクトル"の可能性はありますか? – Pomeron

+0

あなたは100列あるということですか?たぶん、中間ファイルが必要です。 –

0

テストされていないが、アイデアは、グリッドとして、あなたのファイルを扱うことです。あなたは結果が一つのループで出力カラム形式ことができるように

const int COLUMN_COUNT = 2; 
const int COLUMN_WIDTH = 8; 
const int ROW_WIDTH = COLUMN_COUNT * COLUMN_WIDTH + 1; // + 1 is for endl 

void write_cell(std::ostream& out, int row, int column, double value) { 

    // how many rows is there in the file ? 
    out.seekp(0, std::ios_base::end); 
    int row_count = out.tellp()/ROW_WIDTH; 

    // Do we need to create more rows ? 
    for(int i = row_count; i <= row; i++) { 
    out.seekp(ROW_WIDTH - 1, std::ios_base::cur); 
    out << endl; 
    } 

    // compute cell position 
    int pos = row * ROW_WIDTH + column * COLUMN_WIDTH; 

    // move to cell position 
    out.seekp(pos); 

    // write the cell content 
    out << std::setw(COLUMN_WIDTH) << value; 
} 

int main() 
{ 
    std::ofstream fout;  
    fout.open("example.dat"); 

    for (int i=0; i<10; i++) 
    { 
    write_cell(fout, i, 0, Func1(i)); 
    }; 

    for (int i=0; i<10; i++) 
    { 
    write_cell(fout, i, 1, Func2(i)); 
    }; 

    return 0; 
} 
関連する問題