容量の大きいCSVファイルの読み込みについて

このQ&Aのポイント
  • 23メガバイトあるCSVファイルに格納し、datファイルに書き込みを行いたいのですが、実行してみるとセグメンテーション違反が表示され上手くいきません。
  • ファイルを格納し標準出力するまでのプログラムとCSVファイルの内容を記述します。
  • MacOSでの環境です。
回答を見る
  • ベストアンサー

容量の大きいCSVファイルの読み込みについて

容量の大きいCSVファイルの読み込みについて 23メガバイトあるCSVファイルに格納し、datファイルに書き込みを行いたいのですが、実行してみるとセグメンテーション違反が表示され上手くいきません。どなたか具体的に教えてください。 環境はMacOSです。 下にファイルを格納し標準出力するまでのプログラムとCSVファイルの内容を記述します。 //********************************************************************************// #include <stdio.h> #include <string.h> #include <stdlib.h> #define D_LENGTH 10000000000000 struct Data{ double voltage; double pressure; double trigger; }; int main(int argc, char *argv[]) { FILE* fp; // ファイルポインタ用 double ret; int n, i = 0; struct Data *dt; fp = fopen("p37-e1.csv","r"); if (fp == NULL) { printf( "file open error\n" ); exit(EXIT_FAILURE); } dt = (struct Data*)malloc(sizeof(struct Data)*D_LENGTH); while( ( ret = fscanf( fp, "%[^,],%[^,],%[^,],%lf",dt[i].voltage,dt[i].pressure,dt[i].trigger) ) != EOF ){ i++; } printf("\n"); printf("Read File*******************\n"); for (n = 0; n < i; n++) printf("%lf,%lf,%lf\n",dt[n].voltage,dt[n].pressure,dt[n].trigger); free(dt); return(0); } //***************************************************************************// p37-e1.csv //***************************************************************************// 2.329595,0.001373,-4.861982 2.325628,0.001984,-4.744793 2.320745,0.001678,-4.659953 2.319829,0.002289,-4.707866 2.319219,0.002289,-4.699321 2.317082,0.002594,-4.532387 2.312505,0.001984,-4.575723 . . . . //*********************************************//

質問者が選んだベストアンサー

  • ベストアンサー
回答No.1

fscanf( fp, "%[^,],%[^,],%[^,],%lf",dt[i].voltage,dt[i].pressure,dt[i].trigger) が変ですね。 1.[^,]は文字列読み込みなんでdouble型には渡せません。 2.%が4つあるのに後に続く変数が3つなのも変。 double型に読み込ませたいのなら fscanf( fp, "%lf,%lf,%lf\n",&dt[i].voltage,&dt[i].pressure,&dt[i].trigger)

matsuo423
質問者

補足

 ご指摘ありがとうございます。 早速、問題の部分を変更しましたが、実行してみると"Bus error"と表示され上手くいきません。  度々すみませんが、御指南おねがいします。

その他の回答 (3)

回答No.4

#1です。 bus errorね "&"付け忘れてない? &dt[n].voltage,&dt[n].pressure,&dt[n].trigger もしくはmalloc失敗とか

回答No.3

なんで cp や mv や more を使わないのかと思ったら MacOS ですか。 /* Gcc on Mac OSX */ #include <stdio.h> #include <string.h> #include <stdlib.h> #define SIZE 64 #define FILE_NAME "p37-e1.csv" struct Data{ double voltage; double pressure; double trigger; }; int main(int argc, char *argv[]) { FILE* fp; // ファイルポインタ用 int n, i, file_size; struct Data *dat; char buff[SIZE]; if ((fp = fopen(FILE_NAME,"r")) == NULL) { printf( "file open error\n" ); exit(EXIT_FAILURE); } /* 理由:3×8=24 bytes < 「2.329595,0.001373,-4.861982」=27 bytes */ fseek(fp, 0, SEEK_END); file_size = ftell(fp); dat = (struct Data*)malloc(file_size); printf("malloc address= %p, file size= %d\n", dat, file_size); fseek(fp, 0, SEEK_SET); i = 0; while(fgets( buff, SIZE, fp) != NULL ){ dat[i].voltage = atof(strtok(buff, ",")); dat[i].pressure = atof(strtok(NULL, ",")); dat[i].trigger = atof(strtok(NULL, "\n")); i++; } fclose(fp); printf("\n"); printf("Read File (%d lines) *******************\n", i); for (n = 0; n < i; n++) printf("%lf,%lf,%lf\n",dat[n].voltage,dat[n].pressure,dat[n].trigger); free(dat); return 0; }

  • titokani
  • ベストアンサー率19% (341/1726)
回答No.2

>dt = (struct Data*)malloc(sizeof(struct Data)*D_LENGTH); >while( ( ret = fscanf( fp, "%[^,],%[^,],%[^,],%lf",dt[i].voltage,dt[i].pressure,dt[i].trigger) ) != EOF ){ mallocが成功したかどうかチェックしていませんよ。

関連するQ&A

  • csvファイルの読み込み

    fscanf関数を用いて、csvファイルの内容を構造体のそれぞれのメンバに読み込んで表示させようとしているのですが、4列目以降が上手く読み込めません。初歩的な質問で申し訳ありませんがどなたか教えてください。 ****************************ソース************************************************ #include <stdio.h> #include <string.h> #include <stdlib.h> #define SIZE 64 #define FILE_NAME "view_001_McdlData.csv" #define FILE_SIZE 819200 struct Data{ int DataNo; int FrameNo; int SampleNo; char Digital; double voltage; double trigger; double C; double D; }; int main(int argc, char *argv[]) { FILE* fp,*fo, *fi; // ファイルポインタ用 int n, i, file_size; double time,vel[FILE_SIZE]; struct Data *dat; char buff[SIZE]; if ((fp = fopen(FILE_NAME,"r")) == NULL) { printf( "file open error\n" ); exit(EXIT_FAILURE); } fseek(fp, 0, SEEK_END); file_size = ftell(fp); dat = (struct Data*)malloc(file_size); printf("malloc address= %p, file size= %d\n", dat, file_size); fseek(fp, 0, SEEK_SET); i = 0; //データの読み込み while((fscanf(fp, "%d,%d,%d,%s,%lf,%lf,%lf,%lf",&dat[i].DataNo,&dat[i].FrameNo,&dat[i].SampleNo,&dat[i].Digital,&dat[i].voltage,&dat[i].trigger,&dat[i].C,&dat[i].D)) !=EOF ){ printf("%d %d %d %s %lf %lf %lf %lf\n",dat[i].DataNo,dat[i].FrameNo,dat[i].SampleNo,dat[i].Digital,dat[i].voltage,dat[i].trigger,dat[i].C,dat[i].D); i++; } fclose(fp); return 0; } ***********************************csvファイルの内容************************************ 0,1,0,0x3F,2.270000,0.000000,-1.000000,-1.000000 1,1,1,0x3F,2.260000,0.010000,-1.000000,-1.000000 2,1,2,0x3F,2.260000,0.010000,-1.000000,-1.000000 3,1,3,0x3F,2.260000,0.010000,-1.000000,-1.000000 4,1,4,0x3F,2.260000,0.010000,-1.000000,-1.000000 5,1,5,0x3F,2.260000,0.000000,-1.000000,-1.000000 ***************************************************************************************************

  • datファイルの読み込み

    初歩的な質問ですみません。 今、819200行のファイルをfscanfで読み込んで配列に格納しているのですが、実行してみるとBus errorが出力されてしまい、うまく格納できません。どなたか至急教えてもらえませんか? ***************************ソース************************************************************ #include <stdio.h> #include <math.h> #include <string.h> #include <stdlib.h> #define pi 3.1415926535 //円周率 #define FILE_SIZE 819200 #define FILE_NAME "test.dat" struct Data{ int time; double voltage; double velocity; double pressure; double trigger; }; int main() { int k,n,N,i=0,j; struct Data dat[FILE_SIZE]; FILE *fp1; FILE *fp2; if ((fp1 = fopen(FILE_NAME,"r")) == NULL) { printf( "file open error\n" ); exit(EXIT_FAILURE); } //データの読み込み while((fscanf(fp1, "%d %lf %lf %lf %lf",dat[i].time,dat[i].voltage,dat[i].velocity,dat[i].pressure,dat[i].trigger)) !=EOF ){ i++; } fclose(fp1); return 0; } ***************************************************************************************** ********************test.datファイル********************************************** -2.64316 2.329595 0.697657 0.001373 -4.861982 -2.64314 2.325628 0.671961 0.001984 -4.744793 -2.64312 2.320745 0.640333 0.001678 -4.659953 -2.64310 2.319829 0.634400 0.002289 -4.707866 -2.64308 2.319219 0.630449 0.002289 -4.699321 -2.64306 2.317082 0.616607 0.002594 -4.532387 . . . . . *********************************************************************************** 環境はmac osです。 よろしくおねがい致します。

  • CSVファイルの読み込み

    以下のようなCSVファイルを読み込みたいと思っています。 0.575092,0.030525 0.565324,0.018315 0.555556,0.013431 0.553114,0.013431 0.54823,0.015873 0.538462,0.013431 0.531136,0.006105 0.52381,-0.003663 0.516484,-0.010989 0.501832,-0.015873 0.489622,-0.018315 0.477412,-0.020757 0.46276,-0.020757 ・ ・ ・ 50000*2のデータで、以下のようなプログラムを使用しました。 #include <stdio.h> #include <stdlib.h> #include <string.h> /* 確保するデータ保存領域の大きさ(N行×M列) */ #define N 50000 #define M 2 /* データの区切り文字 */ #define SEP_DATA ',' int csv_read(char filename[], double csv[N][M]) { /* ファイルオープン */ FILE *fp; if( (fp = fopen(filename, "r")) == NULL ) { printf(" file open error!!\n"); return -1; } /* 1行毎に読み出し */ char line[256], *ptr; int i, j, k; i=0; while (fgets(line, 256, fp) != NULL) { printf("*%s", line); ptr = line; j=0; do{ /* line[j]から次のタブ文字までを数値に変換 */ csv[i][j] = atof(ptr); /* 次のタブ文字の位置を探す */ ptr = strchr(ptr, SEP_DATA); /* タブ文字の次の文字を示す */ if (ptr!=NULL) { ptr++; } j++; }while(ptr!=NULL && j<M); i++; } /* ファイルクローズ */ fclose(fp); return 0; } int main(int argv, char *argc[]) { char filename[256]; if( argv > 1){ strcpy(filename, argc[1]); } else { printf("Please Input Filename:"); scanf("%s", filename); } /* データ保存用の領域を確保 */ double (*csvdata)[M]; csvdata = (double(*)[M])malloc(sizeof(csvdata) * N); if ( csvdata == NULL ){ return -1; } int i,j; /* 配列の初期化 */ for( i=0; i<N; i++) { for( j=0; j<M; j++) { csvdata[i][j] = 0.0; } } /* CSVデータの読み込み */ if( csv_read(filename, csvdata) < 0 ) { return -1; } /* 配列の出力 */ for( i=0; i<N; i++) { printf("%lf", csvdata[i][0]); for( j=1; j<M; j++) { printf("\t%lf", csvdata[i][j]); } printf("\n"); } free(csvdata); csvdata = NULL; return 0; } しかし、コンパイルは通るのですが実行時にエラーが出てしまいます。 データの大きさに問題があると思うのですが、原因がわかりません。おかしな所のご指摘を頂きたいです。よろしくお願いします。

  • CSVファイルを読み込み構造体のメンバ、"value"に格納し、その後

    CSVファイルを読み込み構造体のメンバ、"value"に格納し、その後平均値を求めて構造体のメンバ、"ave"に格納し表示させたいのですが、読み込み格納している最中で、セグメンテーション違反で終了してしまいます。どなたかよろしければ教えて頂けないでしょうか。 プログラム ************************************************** #include <stdio.h> #include <string.h> #include <stdlib.h> #define SIZE 64 #define FILE_NAME_00 "f_00_01.CSV" struct Data{ double value; double ave; }; int main(int argc, char *argv[]) { FILE* fp,*fo; // ファイルポインタ用 int n, i, file_size; struct Data *dat; if ((fp = fopen(FILE_NAME_00,"r")) == NULL) { printf( "file open error\n" ); exit(EXIT_FAILURE); } fseek(fp, 0, SEEK_END); file_size = ftell(fp); dat = (struct Data*)malloc(file_size); printf("malloc address= %p, file size= %d\n", dat, file_size); fseek(fp, 0, SEEK_SET); i = 0; for(i=0;i<file_size;i++){ fscanf(fp,"%lf",&dat[i].value); printf("%lf\n",dat[i].value); i++; } fclose(fp); printf("\n"); free(dat); return 0; } *************************************************** f_00_01.CSV *************************************************** 2.313725 2.312810 2.314031 2.316167 2.315557 2.313725 . . . . . ***********************************************

  • C言語 ファイルの読み込みについて

    以下のようなプログラムを実行します \nで改行が行われません。なぜでしょうか? #include <stdio.h> void main () { FILE *fp; double a, b; int count=0; fp = fopen("arm_x.csv","r"); while(1) { fscanf(fp,"%lf%lf\n",&a,&b); printf("%f::%f\n",a,b); count++; if(count==10)break; } fclose(fp); } csvファイルは 0.0 0.1 0.2 0.3 0.4 0.5 0.1 0.2 0.3 0.4 0.5・・・ 0.2 0.3 0.4・・・・・・・・・ : : です。 実行結果はこのようになってしまいます。 0.0 0.1 0.2 0.3 0.4 0.5 : :

  • 型によらないCSVファイルの読み込みC言語プログラ

    あらかじめ型のわかっているN行*M列のエクセルデータをCSV形式にし、 読み込むプログラムを作成しました。 そのプログラムを下に示します #include <stdio.h> #include <stdlib.h> #include <string.h> /* 確保するデータ保存領域の大きさ(N行×M列) */ #define N 23 #define M 6 /* データの区切り文字 */ #define SEP_DATA ',' int csv_read(char filename[], double csv[N][M]) { /* ファイルオープン */ FILE *fp; if( (fp = fopen(filename, "r")) == NULL ) { printf(" file open error!!\n"); return -1; } /* 1行毎に読み出し */ char line[256], *ptr; int i, j, k; i=0; while (fgets(line, 256, fp) != NULL) { printf("*%s", line); ptr = line; j=0; do{ /* line[j]から次のタブ文字までを数値に変換 */ csv[i][j] = atof(ptr); /* 次のタブ文字の位置を探す */ ptr = strchr(ptr, SEP_DATA); /* タブ文字の次の文字を示す */ if (ptr!=NULL) { ptr++; } j++; }while(ptr!=NULL && j<M); i++; } /* ファイルクローズ */ fclose(fp); return 0; } int main(int argv, char *argc[]) { char filename[256]; if( argv > 1){ strcpy(filename, argc[1]); } else { printf("Please Input Filename:"); scanf("%s", filename); } /* データ保存用の領域を確保 */ double (*csvdata)[M]; csvdata = (double(*)[M])malloc(sizeof(double[M]) * N); //malloc(sizeof(*csvdata) * N); if ( csvdata == NULL ){ return -1; } int i,j; /* 配列の初期化 */ for( i=0; i<N; i++) { for( j=0; j<M; j++) { csvdata[i][j] = 0.0; } } /* CSVデータの読み込み */ if( csv_read(filename, csvdata) < 0 ) { return -1; } /* 配列の出力 */ for( i=0; i<N; i++) { printf("%lf", csvdata[i][0]); for( j=1; j<M; j++) { printf("\t%lf", csvdata[i][j]); } printf("\n"); } free(csvdata); csvdata = NULL; return 0; } これをNとMがどんな値であれ読み込めるようにするにはどうすれいいでしょうか

  • csvファイルを読み込んで二次元配列に格納したい

    200×250のある数字と文字の入力されたcsvファイル(またはtxtファイル)を読み込んで2次元配列に格納したいのです。 色々調べるとカンマの処理が必要ということがわかりましたが、どのようにソースを書けばよいかわかりません。使用言語はC言語です。 また、実際にcsvファイルを読み込むようにプログラムを書いてみましたが、すべて-858993460となって表示されます。 プログラミング初心者で勉強中なため困っています。 回答よろしくお願いします。 #include <stdio.h> #include <stdlib.h> #define row 200 #define column 250 int main() { int i, j; int data[row][column]; FILE *fp; fp = fopen("sample.csv", "r"); if (fp == NULL){ printf("ファイルがありません\n"); return 1; } for (i = 0; i < row; i++){ for (j = 0; j < column; j++){ fscanf(fp, "%lf", &data[i][j]); } } for (i = 0; i<row; i++){ for (j = 0; j < column; j++){ printf("%3d ", data[i][j]); } printf("\n"); } fclose(fp); return 0; }

  • テキストの読み込みとmalloc()についてです

    こんにちは。 二つのベクトルの次元と要素をテキストファイルから読み取ってそのベクトルの和を出したいのですがうまくいきません。 #include <stdio.h> #include <stdlib.h> double vector_sum(double *x, double *y, int n){ int i; double z[256]={0}; for(i=0;i<n;i++){ z[i] = x[i] + y[i] ; } return *z; } //ベクトル和を出す関数(のつもり)// int main(void){ int i,j,e; double *a,*b,c[256][256]; //a,bはベクトル// FILE *fp; char fname[64]; char str[256]; double z[256]; printf("二つのベクトルが書き込まれているファイル名を入力してください."); scanf("%s",fname); fp = fopen(fname,"r"); if(fp==NULL){ printf("そのようなファイルを見つけることができません。"); } while (fgets(str, 256, fp) >= 0) { i++; fgets(str, 256, fp); printf("%s",str); //テキストの読み取り// if(fgets(str,256,fp)==NULL) break; //読み取り終了時の動作// sscanf(str,"%lf", &c[i]);//c[i][0]は要素数、c[i][1以上]はベクトルの中身を指すことにする。// printf("%lf%lf%lf%lf%lf%lf%lf%lf\n",c[0][0],c[0][1],c[1][2]); if(sscanf(str,"%lf", &c[i])<1){ printf("Format error"); } } if(c[0][0]!=c[1][0]){ printf("要素数が違います。"); } a = malloc(sizeof(double) * c[0][0]); b = malloc(sizeof(double) * c[1][0]); if(a==NULL||b==NULL){ printf("記憶領域の確保に失敗しました。"); } e = c[0][0]; //要素数// for(i=0;i<=e-1;i++){ a[i]=c[0][i+1]; //ベクトルの中身のみをa,bに代入する。// b[i]=c[1][i+i]; } *z= vector_sum(a,b,e); printf("ベクトル和は{"); for(i=0;i<=e-1;i++){ printf("%lf,",z[i]); } printf("}です。"); return 0; } テキストファイルは下のものを使いました。(ファイル名はvector.txt) element: 7 { 4, 4 ,4 ,4 ,4 ,4 ,4 } element: 7 { 8, 8, 8, 8, 8, 8, 8 } 結果は 「二つのベクトル名が書き込まれているファイルを入力してください。(vector.txtを入力) element: 7 { 8, 8, 8, 8, 8, 8, 8 } 要素数が違います。記憶領域の確保に失敗しました。ベクトル和は{}です。」 と表示されてしまい、困っています。 初歩的なミスかもしれず恐縮ですがよろしければ回答お願いします。

  • C言語でファイルから読み込みができません。

    以下のプログラムを実行すると よくわからない値が返ってきます。 なぜでしょうか?教えてください。 #include <stdio.h> void main () { FILE *fp; double a, b; int count=0; fp = fopen("test.xls", "r"); while(1) { fscanf(fp, "%lf %lf\n", &a, &b); printf("%f, %f\n", a, b); count++; if(count==10)break; } fclose(fp); } test.xlsの中身は 1.0 2.0 3.0 4.0 5.0 6.0   :   :   :   : です。 よろしくお願いします。

  • C言語のプログラミングで困っています

    C言語を勉強しています。まだまだ初心者で分からないことだらけなのですが、今回はファイル入出力の部分が分からず苦戦しています。 『100個の実数が入った2つのテキストファイルから数値を読み込み、  絶対値を求めるなどの計算をする』プログラムを作成しているのですが、 コンパイルし実行すると強制終了してしまいます。 プログラムは、 void main(void) { FILE *fp; double c[50000];   double d[50000];   double e[50000]; int n = 0;   int m = 0;   int i = 0;   char fname[80];   char fname2[80]; printf("ファイル名 : ");    gets(fname); if((fp = fopen(fname, "r")) == NULL){ printf("ファイルがオープンできません\n"); exit(1); } printf("\n"); while (fscanf(fp,"%lf",&c[i])!=EOF){ printf("%3d : %3lf",++n,c[i]); printf("\n"); i++; } printf("\n"); i=0; n=0; printf("ファイル名 : ");    gets(fname2); if((fp = fopen(fname2, "r")) == NULL){ printf("ファイルがオープンできません\n"); exit(1); } printf("\n"); while (fscanf(fp,"%lf",&d[i])!=EOF){ printf("%3d : %3lf",++n,d[i]); printf("\n"); i++; } …(以下計算) のようになっています。 整数のデータで計算を行うと、正常に動くのですが…。 コンパイルしてもエラーが出ないので、どこが悪いのかわからず困っています。 どなたか教えていただけないでしょうか。お願いしますm(_ _)m

専門家に質問してみよう