2015-12-14 12 views
5

タイトルと同じように、私はファイルから不定数の整数を読み込み、2次元配列に配置しようとしています。C++で長さを知らずにファイルから2次元配列を読み取る方法は?

#include <iostream> 
#include <fstream> 
using namespace std; 
int main() 
{ 

fstream f;int i,j,n,a[20][20];char ch; 

i=0;j=0;n=0; 
f.open("array.txt", ios::in); 
while(!f.eof()) 
{ 
    i++; 
    n++; 
    do 
    { 
     f>>a[i][j]; 
     j++; 
     f>>ch; 
    } 
    while(ch!='\n'); 
} 

for(i=1;i<=n;i++) 
{ 
    for(j=1;j<=n;j++) 
     cout<<a[i][j]<<endl; 
    cout<<endl; 
} 
return 0; 

}

と私の "array.txt" ファイル:

1 1 1 
2 2 2 
3 3 3 

プログラムをコンパイルした後、それはあなたが見てみたいことがあります。この

enter image description here

+1

は、あなたが ''しばらく(!CH = '\ n' の)を意味するものではありませんか?編集:また、 'f >> ch'と' f >> a [i] [j] 'の順番を逆にしたいかもしれません。 – forkrul

+0

ようこそスタックオーバーフロー。出力へのリンクを投稿せず、実際の出力を投稿してください。より単純なものを試してみましょう:単純な(1D)配列に読み込みます。 'while(!f.eof())'は使わないでください。 – Beta

+0

私はあなたの提案を試みます。編集:それは何も返しません。 – NacRonDX

答えて

3

入力ファイルが行指向であるため、行を読み取るにはgetline(C++またはC fgets)を使用し、次に行を整数に解析するにはistringstreamを使用する必要があります。 先験的なのサイズを知りませんので、ベクトルを使用して、すべての行が同じサイズで、行数が列数と同じであるように一貫して制御する必要があります。

最後に、の直後にeof をテストして、ループの始めにはテストしないでください。

コードは次のようになります。

#include <iostream> 
#include <fstream> 
#include <vector> 
#include <string> 
#include <sstream> 
using namespace std; 
int main() 
{ 

    fstream f; 
    int i=0, j=0, n=0; 
    string line; 
    vector<vector<int>> a; 
    f.open("array.txt", ios::in); 
    for(;;) 
    { 
     std::getline(f, line); 
     if (! f) break; // test eof after read 
     a.push_back(vector<int>()); 
     std::istringstream fline(line); 
     j = 0; 
     for(;;) { 
      int val; 
      fline >> val; 
      if (!fline) break; 
      a[i].push_back(val); 
      j++; 
     } 
     i++; 
     if (n == 0) n = j; 
     else if (n != j) { 
      cerr << "Error line " << i << " - " << j << " values instead of " << n << endl; 
     } 
    } 
    if (i != n) { 
     cerr << "Error " << i << " lines instead of " << n << endl; 
    } 

    for(vector<vector<int>>::const_iterator it = a.begin(); it != a.end(); it++) { 
     for (vector<int>::const_iterator jt = it->begin(); jt != it->end(); jt++) { 
      cout << " " << *jt; 
     } 
     cout << endl; 
    } 
    return 0; 
} 
1

を印刷しますあなたは動的配列を持つことができるようにベクトルを使用します。

0

試してみてください。

#include <iostream> 
#include <fstream> 
#include <sstream> 
#include <string> 
using namespace std; 
int main() { 
    fstream f; 
    int i, j, n, a[20][20]; 
    string buf; 

    i = 0; 
    j = 0; 
    n = 0; 
    f.open("array.txt", ios::in); 
    while (1) { 
    getline(f, buf); 
    if (f.eof()) break; 
    stringstream buf_stream(buf); 
    j = 0; 
    do { 
     buf_stream >> a[i][j]; 
     j++; 
    } while (!buf_stream.eof()); 
    i++; 
    n++; 
    } 

    for (i = 0; i < n; i++) { 
    for (j = 0; j < n; j++) cout << a[i][j] << " "; 
    cout << endl; 
    } 
    return 0; 
} 

また、あなたが本当に任意の大きさの配列を読みたい場合は、std::vectorまたはそのようないくつかの他の容器ではなく、生の配列を使用する必要があります。

+1

'while(1)'の代わりに 'while(getline(f、buf))'と別の 'getline'と' if'と 'break'を調整することをお勧めします。また、 'getline'でストリームエラーが発生しても、eofがなくても' buf'の内容が未定義になるのを防ぐことができます。 – user4581301

関連する問題