• 締切済み

ファイルへの書込み処理が異常に遅い

以下のファイルへの書込みを行なうプログラムの処理速度が極端に遅く困惑しています。 -------------------------------------------------------------------------------- /*  文字列"0,"をファイルに約2MB出力するプログラム  (2000文字で改行、1行毎にfopen&fclose) */ #include<stdio.h> void main( int argc, char *argv[] ) {   FILE *fp;   for( int i = 0; i < 1000; i++ )   {     if( !(fp = fopen( "C:\hogehoge.log", "a" ) ) )     {       exit( 1 );     }     for( int j = 0; j < 1000; i++ )     {       fprintf( fp "0," );     }     fprintf( "\n" );     fclose( fp );   }   exit( 0 ); } -------------------------------------------------------------------------------- 処理時間は5分程度です。 出力する文字列を"0#"に変えると5~6秒で終了します。 カンマが入ると違うのでしょうか? OSはWinXP、コンパイラはVC++7.0です。 原因と解決策をご存知の方、よろしくご教示下さい。

みんなの回答

  • t_nojiri
  • ベストアンサー率28% (595/2071)
回答No.5

ちなみに、バイナリモードであけて、最後尾にはfseekでディスクリプター飛ばした方が、速いと思いますよ。 変にテキスト処理をfopenにさせてるのが問題なんで。 まあ、処理時間計測するなら、各APIの呼び出しと返却毎にタイム計測して、原因特定するのが普通ですけどね。

  • jacta
  • ベストアンサー率26% (845/3158)
回答No.4

よく見ると、 fprintf( fp "0," ); の部分もfpの後のコンマが抜けていますね。 それに、 fopen( "C:\hogehoge.log", "a" ) のとことでも、\\ではなく\になっています。 というわけで、このソースがコンパイルできる可能性は皆無です。 実際に使用したソースコードを補足してください。

heikki_sorse
質問者

補足

回答ありがとうございます。 申し訳ありません、実機ではネットができない&持ち出し不可のため質問のプログラムは手でタイプしたものです。 fopen( "C:\\hogehoge.log", "a" ) fprintf( fp, "0," ); fprintf( fp, "\n" ); の誤りです。

  • jacta
  • ベストアンサー率26% (845/3158)
回答No.3

本当にこのプログラムで(実行時間はともかく)動いたのでしょうか? fprintf( "\n" );の部分は、第1引数にFILE*型でストリームを指定する必要があるはずです。これがコンパイルできるということは、stdio.hが破壊されているか、全く別の(素性不明の)stdio.hがインクルードされているものと思われます。

  • a-saitoh
  • ベストアンサー率30% (524/1722)
回答No.2

fprintfがカンマを認識して何かしているのかなぁ。  fprintf( fp "0," ); を、 fputc('0',fp);fputc(',', fp); に変えても速度は変わりませんか? それと、何で1行ごとにfopen/closeしなければいけないのか理解に苦しみます。

heikki_sorse
質問者

お礼

回答ありがとうございます。 fputc()でも試しましたが同じでした。 実際作りたいプログラムはもっと煩雑です。 詳しくは申し上げませんが1行毎にfopen、fcloseを前提とした回答をお願い致します。 知りたいのは「カンマが入るとなぜファイル出力が遅いのか」ということです。

  • t_nojiri
  • ベストアンサー率28% (595/2071)
回答No.1

ファイルポインタ、テキストの追記で開けば、カンマ等は区切り文字扱いだから劇的に遅くなります。 まあ、普通同一ファイルをループの中で開けてる、しかもfseek()等してないなら、バグですね。

heikki_sorse
質問者

お礼

回答ありがとうございます。 んー、カンマがあると遅くなるのですね。。。 質問のプログラムは簡易に書きましたが、実際に作りたいプログラムはファイル出力以外にも処理があり、1行毎にfopen、fcloseは必須と考えています。 いま実機が無いので確認できませんが、fseek()を試してみます。

関連するQ&A

  • ファイルへの書き込みについて

    はじめまして、よろしくお願いします。 <質問>C言語を使用したプログラミングで、     下記ソースのように、     ファイルへ書き込むことは可能であればご指摘お願いします。     ※上手に値が渡せていないようで、      実行すると不正な処理?で落ちてしまいます。 <書き込む方法>     1)メインプログラムで書き込むファイルのOPEN     2)サブプログラムで処理を行いファイル書き込み(1)       サブプログラムで処理を行いファイル書き込み(n)     3)メインプログラムで書き込んだファイルをCLOSE <イメージ> #include <stdafx.h> #include <stdio.h> void sub( int i, FILE *fp ); int main(){ FILE *fp; fp = fopen("c:\\0511.txt","w"); int i; for( i = 1; i < 100; i++ ){ sub( i, fp ); } fclose(fp); } void sub( int i, FILE *fp ){ char moji[2]; sprintf(moji,"%3d",i ); fprintf(fp,"%s",moji ); } <補足>VC++2005 ExpressEdition でビルドは出来ました。 お手間おかけしますが、よろしくお願いします。

  • コマンドラインによるファイル名指定

    #include<stdio.h> #include<stdlib.h> int main(int argc,char *argv[]) { FILE *fp,*fpc; int i=0; char line[1000]; fp = fopen("test.txt","r"); if(fp == NULL) { printf("File not found.\n"); exit(1);  }  fpc = fopen(argv[1],"w"); if(fpc==NULL){ fprintf(stdout,"Can not open file.\n"); exit(1); } while(fgets(line[i],1000,fp)!=NULL){ i++; } for(i=3;i<0;i--){ fprintf(fpc,"%s",line[i]); } fclose(fp); fclose(fpc); return 0; } コマンドラインでファイル名を指定し、そのファイルに、test.txt(4行の文字列)の内容を各行を逆順に書き出すプログラムですが、上手くいきません。ご指摘を願いします。

  • ファイルの入出力

    学生です。まだ習い始めて間もないのですがよろしくお願いします。 27.000000,207.000000,116.000000 48.000000,90.000000,116.000000 48.000000,90.000000,116.000000       : テキストの中にある上記のカンマ区切りのデータをfscanfで読み込んで違うテキストに同じ数値を出力したいのですがうまく出力できません。 0.000000,0.000000,+NAN 0.000000,0.000000,+NAN 0.000000,0.000000,+NAN      : 数値は上記のように出力されてしまいます。 プログラムは以下の通りです。 main() { FILE *fp; double m[30][3]; int i,j; double e1,e2,e3; fp=fopen("data00.txt","r"); for(i=0;i<30;i++){  fscanf(fp,"%f,%f,%f\n",&e1,&e2,&e3);  m[i][0]=e1;  m[i][1]=e2;  m[i][2]=e3; } fclose(fp); fp=fopen("data01.txt","w"); for(j=0;j<30;j++){  fprintf(fp,"%f,%f,%f\n",m[j][0],m[j][1],m[j][2]); } fclose(fp); getch(); exit(0); } データの読み込みがうまくいってないのだと思いますがわかりません。 間違いがあったならご指摘お願いします。

  • ファイル

    c言語初心者です。 どなたか教えていただけませんか? これだとiが定義されないことになってしまいます。 #include<stdio.h> #include<stdlib.h> int main() { FILE *fp; fp=fopen("monai", "w"); if(fp==NULL){ fprintf(stderr,"ファイルのオープンに失敗しました。\n"); exit(0); } int i; for(i=1;i<=30;i++) { if(i<=9){ fprintf(fp," %d ",i); } else if(i%10==0) { fprintf(fp,"%d\n",i); } else { fprintf(fp,"%d ",i); } } fclose(fp); return 0; } ビルドもできません。

  • ファイル入力

    1 20 2 30 3 95 4 52 5 90 3 Maximum  上記の様な入力ファイルinput.datのうち1~5行目のデータを表示するプログラムを作っています。  6行目は空白で、7行目は2列目の中で最大値をとる行の1列目の数値が入っています。  1列目の数値は最後の行を除いて重複することはありません。  入力データの行数はファイルによって最大20行まで変動します。列数は2列で固定です。  以下のプログラムのままでは6行目以降のデータも読み取ってしまい、出力がおかしくなってしまいます。  1~5行目のデータのみ出力するにはどうしたらよいでしょうか。  ご存知の方、お手数ですが教えてください。よろしくお願いします。 #include <stdio.h> #include <stdlib.h> #define row 20 #define col 2 int main(){ int i,j,data[20][2]; FILE *fp; if((fp=fopen("input.dat","r"))==NULL){ fprintf(stderr,"Cannot open file input.dat\n"); exit(1); } for(i=0;i<row;i++){ for(j=0;j<col;j++){ fscanf(fp,"%d",&data[i][j]); printf("%d ",data[i][j]); } printf("\n"); } fclose(fp); return 0; }

  • ファイル入出力について教えて下さい。

    ご覧いただきありがとうございます。 数値を入力して、数値を出力する方法を教えて頂きたいです。 ・   ・   ・ fp = fopen( "a.txt", "a" ); for( i = 16383; i >= 0; i-- ) { fprintf( fp, "%d", i ); } fclose( fp ); ・   ・   ・ data = (int *)malloc(32768); fp = fopen( "a.txt", "r" ); for( i = 0, i <= 16383; i++ ) { fscanf( fp, "%d", data+i ); } fclose( fp ); ・   ・ ・ 以上の記述で、入力はうまくいくのですが、出力の際に数値でなくなってしまいます。どうしてでしょうか? ご存じの方がおりましたら、ご回答よろしくお願いいたします。

  • バイナリファイル(画像)のよみこみ

    レポートで1024×1024ピクセルの画像を、間引いて256×256の画像にしろというのが出されました。画像はrawファイルです。 それで、とりあえず画像を読み込んで、出力するプログラムを書いてみたんですが、コンパイルは出来るのに実行すると不正な処理とけいこくがでてきてしまいます。 ソースは #include<stdio.h> main() { unsigned char in[1024][1024],out[1024][1024]; FILE *fp; int i,j; fp=fopen("aaa.raw","rb"); fread(in,sizeof(unsigned char),1024*1024,fp); fclose(fp); for(i=0;i<1024;i++){ for(j=0;j<1024;j++) out[i][j]=in[i][j]; } fp=fopen("bbb.raw","wb"); fwrite(out,sizeof(unsigned char),1024*1024,fp); fclose(fp); } です。 どこがいけないのかアドバイスいただきたいです。よろしくお願いします。

  • ファイル書き込み操作について

    C言語でファイル書き込みを行う以下のプログラムを改造したいと思っています。 #include <stdio.h> #include <stdlib.h> int main() { char filename[10] = "output"; char strs[][10] = { "1.aaa\n" ,"2.\n" ,"3.\n" } FILE* fp; int i; int length; fp = fopen(filename , "w"); if (fp == NULL) { printf("cannot open file\n"); exit (1); } length = sizeof(strs)/10; for( i = 0; i < length ; i++ ) { fputs( strs[i], fp ); } fclose(fp); return 0; } この場合、outputの内容は、 1.aaa 2. 3. となりますが、 2行目にはscanf等を使いプロンプトから読み込んだbbbという文字列、 3行目にはtxtファイルから読み込んだcccという文字列を書き込むというような仕様にしたいと思っています。 その結果outputは、 1.aaa 2.bbb 3.ccc となるようにしたいです。 サンプルを改良してこのような仕様を満たすプログラムができますでしょうか?回答よろしくお願いします。

  • テキストファイルの出力について

    今、学校の課題でC言語を使ってプログラムを作っています。 20000個のデータを読み込んで、200個ずつに区切り、別々のテキストファイルで出力するというものです。 最初につくったのは、以下の通りです。 *********************************************** FILE *fp; { int b,i=0; data[0][i]=trend_data[0][i]; data[1][i]=trend_data[1][i]; fp = fopen("D1.txt","w"); for(i=0;i<=199;i++){ fprintf(fp,"%8.8f %8.8f\n",data[0][i],data[1][i]); } fclose(fp); fp = fopen("D2.txt","w"); for(i=200;i<=399;i++){ fprintf(fp,"%8.8f %8.8f\n",data[0][i],data[1][i]); } fclose(fp); ・・・ ***************************************** これだと20000まで繰り返し記述しなければならずかなり困難だと思いました。そこで、ループを作ろうとしたのですが、テキストファイルをループを使って複数作成する方法がわかりません。 以下のようなプログラムを作ったのですが、テキストファイルが一つしか作られませんでした。 どのように記述すればよいのでしょうか? **************************************** FILE *fp; { int a,i=0; int b=1; int c=199; data[0][i]=trend_data[0][i]; data[1][i]=trend_data[1][i]; start: fp = fopen("D[1+b].txt","w"); for(i=a;i<=c;i++){ fprintf(fp,"%8.8f %8.8f\n",data[0][i],data[1][i]); if(i > c) c = c+200; a = a+200; b++; goto start; fprintf(fp,"%8.8f %8.8f\n",data[0][i],data[1][i]); fclose(fp); } } ****************************************** よろしくお願い致します。

  • ファイル

    AからZまでの文字が何回出力されるか数えるプログラムなのですが、うまく出力されません。 どこを変えればよろしいでしょうか。 #include<stdio.h> #include<stdlib.h> #include<ctype.h> int count[26]; int main(void) { char str[100] = "xyzYZZ\n"; FILE *fp; char *p; int i; char ch; if((fp = fopen("myfile","w")) == NULL){ printf("ファイルを開くことが出来ません"); exit(1); } p = str; while(*p){ if(fputc (*p,fp) == EOF){ printf("ファイル書き込みエラー"); exit(1); } p++; } fclose(fp); if((fp = fopen ("myfile","r")) == NULL){ printf("ファイルを開くことが出来ません"); exit(1); } while((ch == fgetc(fp)) != EOF){ ch = toupper(ch); if( ch >= 'A' && ch <='Z' ) count[ch - 'A']++ ; } for( i=0 ; i<26 ; i++) printf("%c は %d 回出現\n",i + 'A', count[i]); fclose(fp); return 0; }

専門家に質問してみよう