• 締切済み

データの読み込みがうまくいかなくて、困っています

プログラミング初心者です。 誤差逆伝播学習のプログラムを行っています。 C言語で、データの読み込み部分がうまくいかなくて、困っています。 borland , BCC Developerなどを用いてやっております。 やりたいことは、テキストファイルから数字を読み込み、それを行列に格納してデータとして送るということです。 その際に、テキストファイルで行と列で表示されたものを送ろうと考えています。30×30の、1と0で表示された絵と教師信号を読み取っています。 列だけの読み込みは正常に動いたのですが、行と列で表示されたものの読み込みができません。char型で変数を宣言しているので、数字として読み込めていないとか、そういったことがあるのでしょうか。o1[][],t[][]の部分に正しく値が送れるようにしたいです。 非常にわかりにくくて申し訳ないのですが、お分かりになる方がいたら、どこをどう変えれば良いか、教えて頂きたいです。 「間違っている列と行の読み込み」 //データをファイルから読み込む// void read_file(name) char *name; { int i,j,k; //ループカウンター// FILE *fp; //ファイルポインタ// char buff[MCHS]; //buffの最大文字数1024 //ファイルオープン// if((fp=fopen(name,"r"))==NULL){ fprintf(stderr,"%s:File open error !!\n",name); exit(-1); } //学習データを読み込む// fscanf(fp, "%d",&learning_pattern_no); //学習パターンの数読み込み fscanf(fp,"%d",&test_pattern_no); //テストパターンの数読み込み printf("学習パターンの数:%d\n",learning_pattern_no); //学習パターンの数表示 printf("テストパターンの数:%d\n",test_pattern_no); //テストパターンの数表示 i=0;j=0; while( fgets( buff, MCHS, fp ) != NULL ){ if(j<=learning_pattern_no+test_pattern_no-1){ for( k=0; k<MCHS; k++ ){ o1[j][i+k]=buff[k]; //o1[j][i+k]にbuff[k]を入れる printf("%c",buff[k]); //printfで確認 if( buff[k] =='\n'){ i=i+k; if (i==InputUnitNo){ i=0; j++; printf("%d",j); }//if(i==InputUnitNo)終了 break; }//if(buff[k])終了 }//for終了 }//if(j<=learn+test)終了 else{ //ここから教師信号の読み取り for( k=0; k<MCHS; k++ ){ t[i][k]=buff[k]; printf("%c",buff[k]); //教師信号の確認 if( buff[k] == '\n' ){ i++; break; }//if(buff[k])終了 }//for終了 }//else終了 }//while終了 } 「正常に動いた列だけの読み込み」 //データをファイルから読み込む// void read_file(name) char *name; { int i,j; //ループカウンター// FILE *fp; //ファイルポインタ// //ファイルオープン// if((fp=fopen(name,"r"))==NULL){ fprintf(stderr,"%s:File open error !!\n",name); exit(-1); } //学習データを読み込む// fscanf(fp, "%d",&learning_pattern_no); printf("学習データの数:%d\n",learning_pattern_no); for(i=0;i<learning_pattern_no; i++){ for(j=0;j<InputUnitNo; j++) fscanf(fp,"%lf",&o1[i][j]); for(j=0;j<OutputUnitNo; j++) fscanf(fp,"%lf",&t[i][j]); //教師信号 } //テストデータを読み込む// fscanf(fp,"%d",&test_pattern_no); printf("テストデータの数:%d\n",test_pattern_no); for(i=learning_pattern_no;i<learning_pattern_no+test_pattern_no;i++) for(j=0;j<InputUnitNo;j++) fscanf(fp,"%lf",&o1[i][j]); fclose(fp); }

みんなの回答

  • Tacosan
  • ベストアンサー率23% (3656/15482)
回答No.3

.... 単純に「fgets で読み込んでいるので, 全て文字として入力されている」だけ? 上の「間違っている列と行の読み込み」で, o1[j][i+k]=buff[k]; //o1[j][i+k]にbuff[k]を入れる の次に printf("%f\n", o1[j][i+k]); という行を追加して o1 の中身を表示させてみてください. どのような値が表示されますか? あ, ついでだけど o1 は double の配列ってことでいいんですよね?

akasa111
質問者

補足

お返事ありがとうございます。 試してみたところ、0.480000という数字がたくさん出てき、 「printf("%c",buff[k]); //printfで確認」の部分の1と0で表せられていた画像が消えてしまいました。 o1はdoubleの配列です。わかりづらくて、すみません。

  • Tacosan
  • ベストアンサー率23% (3656/15482)
回答No.2

もちろん「char で読み込んだ」ら '0' とか '1' という値になるわけで, これは (一般には) 0 や 1 という整数値とは異なります. あと, その「テキストデータ」のフォーマットを詳しく説明してもらえませんか? 特に「0 と 1 で表示された絵」の部分で, 各データの間に空白があるかどうかがちょっと気になります. ついでに余談だけど, いまさら void read_file(name) char *name; という形の関数定義をするべきではありません. void read_file(const char *name) くらいにしましょう (ファイル名を変更することはないと思うので const も追加してみました).

akasa111
質問者

お礼

cortotbachさん、Tacosanさんお返事ありがとうございます。 テキストファイルはこのようになっております。 4 //学習パターン数 2 //テストパターン数 000000000000000000000000000000 000000000000000000000000000000 000000000000000000000000000000 000000000000000000000000000000 000000000000000000000000000000 000000000000000000000000000000 000000000000000000000000000000 000000000000000000000000000000 000000000000000000000000000000 000000000000000000000000000000 000000000000000000000000000000 000000000000000000000000000000 000000000000000000000000000000 000000000000000000000000000000 000000000000000000000000000000 111111111111111111111111111111 111111111111111111111111111111 111111111111111111111111111111 111111111111111111111111111111 111111111111111111111111111111 111111111111111111111111111111 111111111111111111111111111111 111111111111111111111111111111 111111111111111111111111111111 111111111111111111111111111111 111111111111111111111111111111 111111111111111111111111111111 111111111111111111111111111111 111111111111111111111111111111 111111111111111111111111111111 以下、一行空けて、同じような30×30の画像(数字)が続く形になっています。そして、最後に認識番号のような教師信号を1000,0100と入る形になっています。一行空けるのは、画像と画像がくっついてしまうと、わかりづらくなってしまうと思ったからです。

回答No.1

質問のされ方をもう少し工夫した方が良いですね。 データの入っているテキストデータのフォーマットを明確にしないとよくわかりません。 課題かレポートなのかもしれませんが、それでも条件・課題内容と不明な点をもう少し説明された方が良いと思います。 ヒントですが、 fscanf(fp, "%d",&learning_pattern_no); //学習パターンの数読み込み というように1行読み込みを上部で使っているのであれば、 while( fgets( buff, MCHS, fp ) != NULL ){ このような取得の方法ではなく、同じように1行ずつ読んでいけば簡単かと思います。データは行と列のテキスト(ASCII)なのですよね? たとえば、 int line[30]; fscanf(fp, "%d %d %d......", line[0], line[1], line[2],....); みたいな感じで(列が半角スペース区切りの場合ですが)、1行を一気に読んでしまえば良いかと思います。 それを30行分繰り返すなど。あんまり美しくは無いですが。

関連するQ&A

  • scanf C言語

    現在取得したデータを多次元配列いれたいのですが、カンマまでの文字列を入れる方法がわかりません。例で言いますと jgasogasog,dklafh343,fdjalsjfd,kldjfas5 dfasfdas6ff ,fsadfa6sg,dgas6dsa,fsdafa もカンマまでの文字列array[0][0] = jgasogasog array[0][1] = dklafh34 といった形で入れていきたいです。 ご迷惑おかけしますが何卒よろしくお願いします。 途中まで作ったソースをのせます。 #define _CRT_SECURE_NO_WARNINGS #include <stdio.h> #include <stdlib.h> #include<string.h> #define piyo 2 #define hoge 1400 int main(void) { FILE *fp; char test[10][500]; int n = 0; if ((fp = fopen("testfile.csv", "r")) == NULL) { printf("\aファイルをオープンできません\n"); return(0); } int i, j; int k = 0; //ファイルfpの終端指示子をチェックします。 while (!feof(fp) && k < 500) { //%cは一文字出力をしてくれる使用データ型はchar型 //fscanf関数は書式指定をしてファイルから値を読み込み、バッファに格納します。 for (i = 0; i < 10; i++) { for (j = 0; j < 500; j++) { fscanf(fp, "%[^,],%d", &test[i][j]); k++; } } } for (i = 0; i < 10; i++) { for (j = 0; j < 500; j++) { printf("test[%d][%d]=%d\n", i,j,test[i][j]); } } fclose(fp); return(0); } 似たような質問をしてすいません。

  • 単語の出現頻度を調べるプログラム

     ファイルからデータを読み込んで、単語の出現頻度を調べるプログラムを作ろうと考えて、下記のようなプログラムを書いてみました。 #include <stdio.h> #include <string.h> main() { struct data {char word[128]; int freq;} word_data[128]; char words[128]; char term[128]; int i=0; int nw=0; int j; char buff[128]; FILE *fp_in=fopen("data.txt","r"); while(fgets(fp_in,128,buff)!=EOF){ char buff[128]; int k; for(k=0;k<=128;k++){ printf("%s",buff); if(('A'<=buff[k] && buff[k]<='Z')||('a'<=buff[k] && buff[k]<='z')) term[i++]=buff[k]; else if(i>0) term[i]='\0';} for(j=0;j<nw;j++){ if(strcmp(term,word_data[j].word)==0) break; if(j==nw) {strcpy(word_data[j].word,term); word_data[j].freq=1; nw++;} else if(j!=nw) {word_data[j].freq++; i=0;} }} for(j=0;j<nw;j++) printf("%s %d",word_data[j].word,word_date[j].freq); return 0;} コンパイルは通ったのですが、実行しても画面に何も表示されません。原因は何処にあるのでしょうか?分かる方がいましたら、ご回答宜しくお願いします。

  • printfの挿入箇所

    #include <stdio.h> #include <stdlib.h> #define N 500 void bubblesort(int h, int k, int *A); void swap(int i, int j, int *A); int main(void) { int A[N]; int n, i; FILE *file; file=fopen("sortdata", "r"); /* データの読込み */ fscanf(file, "%d", &n); if(n>N) { printf("Illegal array size n = %d for N = %d\n", n, N); exit(1); } for(i=0; i<n; i++) fscanf(file, "%d", &A[i]); /**/ printf("A = "); /**/ printf("\n"); bubblesort(0, n-1, A); /* 配列A[0]からA[n-1]の整列 */ return(0); } /* A[k],...,A[h]の要素をバブルソートによって整列 */ void bubblesort(int h, int k, int *A) { int i, j, p; int no; int test; /* test==1; すでに整列済み */ for(i=h; i<k; i++) /* バブル操作の反復 */ { test=1; for(j=k; j>=i+1; j--) { for(no=0; no<j; no++) printf(" %d",A[no]); if(A[j]<A[j-1]) { printf(" > %d ",A[j]); swap(j, j-1, A); test=0; } else { printf(" < %d ",A[j]); } for(no=j+1; no<=k; no++) printf(" %d ",A[no]); printf("\n"); } printf("\n"); if(test==1) return; } return; } /* Swap A[i] and A[j]. */ void swap(int i, int j, int *A) { int temp; temp=A[i]; A[i]=A[j]; A[j]=temp; return; } 以上のプログラムを A = パス1: 7 5 1 2 8 > 3 7 5 1 2 < 3 8 7 5 1 < 2 3 8 7 5 > 1 2 3 8 7 > 1 5 2 3 8 1 7 5 2 3 8 パス2: 1 7 5 2 3 < 8 1 7 5 2 < 3 8 1 7 5 > 2 3 8 1 7 > 2 5 3 8 1 2 7 5 3 8 パス3: 1 2 7 5 3 < 8 1 2 7 5 > 3 8 1 2 7 > 3 5 8 1 2 3 7 5 8 パス4: 1 2 3 7 5 < 8 1 2 3 7 > 5 8 1 2 3 5 5 8 パス5: 1 2 3 5 7 < 8 1 2 3 5 7 8 比較は15回でした。 交換は8回でした。 と表示させたいのですがうまくいきません。 どなたかご指導よろしくお願いします

  • C言語で複数列のデータを1列のみ読み込みたい

    行m列の任意のデータの処理を行うプログラムで, 列ごとの統計を行うためにm列目のデータを取り出したいのですが,うまくいきません. どのようなコードを書けばいいでしょうか? 自分で作ってみたのは以下のようなプログラムです(ファイルを開いて→m列目の読み込みの部分) EOFを使っているためか,行数のiには全データ数が入ってしまいます. void main (void) { FILE* fp; int i, j; i=0, j=0; char FilePath[500]; char Folder[100]; char File[50]; printf("Folder Name:"); scanf("%s",&Folder); printf("File Name:"); scanf("%s",&File); sprintf(FilePath,"%s/%s",Folder,File); if(( fp = fopen (FilePath,"r")) == NULL){ printf("cannot open '%s'\n", FilePath); exit(1); } //ここまではうまく動きます while (fscanf(fp, "%lf", &A[i][0]) != EOF{ i++; } while (fscanf(fp, "%lf", &A[0][j]) != EOF){ j++; } printf("A[%d][%d]", i, j); int n, m;              //n,mはこの後for文で使いたいので登場してもらいました printf("input 'n':"); scanf("%d", &n); printf("input 'm':"); scanf("%d", &m); }

  • 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です。 よろしくおねがい致します。

  • ライブラリ関数について教えてください

    C言語を独学で勉強しています。 ファイルの中のデータと配列データが一致するかを調べるプログラムを作ろうとしています。 しかし、私が作っているプログラムでは表示結果が正しくありません。 char型では==を使って一致かどうかを調べることが出来ないので、ライブラリ関数を使う必要があることを知ったのですが、調べてもよくわかりませんでした・・・ どのように作ればいいのか詳しく教えていただけないでしょうか。 よろしくお願いします。 #include<stdio.h> struct test { char no[5]; char name[10]; char english[5]; char math[5]; }; int main(void){ FILE *fp; int i; char f_no[5], f_name[5]; struct test data[5] = { {"001","akemi","100","40"}, {"002","tadao","59","76"}, {"003","mika","94","69"}, {"004","hiroshi","54","98"}, {"005","kazu","39","57"} }; struct test *test_p; test_p = data; if ((fp = fopen("test.txt", "r")) == NULL) { printf("NOT OPEN FILE\n"); } else { while (fscanf(fp, "%s%s", f_no, f_name) == 2) { for(i = 0; i<=5; i++) { if((test_p->no == f_no) && (test_p->name == f_name)) { printf("%s %s 英語%s 数学%sです。\n", f_no, f_name, test_p->english, test_p->math); } else { printf("%s %s 一致しません\n", f_no, f_name); break; } ++test_p; } } } fclose(fp); }

  • C言語のファイル操作についての質問です

    #include <stdio.h> #include<process.h> int main(void) { FILE *fp; int a[200], i, j, cnt, max, max_i; fp = fopen("data.txt", "r"); if (fp == NULL) { printf("file cannot open.\n"); exit(1); } for(i = 0; i < 200 && fscanf(fp, "%d", &a[i]) == 1; ++ i) ; fclose(fp); for(max = max_i = j = 0; j < i; ++ j){ int k; for(cnt = 0, k = j + 1; k < i; ++ k) cnt += (a[j] == a[k]); if(cnt > max) max = cnt; max_i = j; } printf("%d\n", a[max_i]); return 0; } これは「data.txt」というファイルから最頻値を探し出し、その値を表示するプログラムです。 しかし、このプログラムだと最頻値が1つしか表示できないので、 最頻値が複数ある場合でも、すべての最頻値の値を表示させるようなプログラムに書き換えてほしいです。 よろしくお願いします。 例)data.txt 30000 100 150 30000 30000 100 4320 100 出力↓ 30000 100

  • ファイルポインタによるコアダンプの解決法

    タイトルの通りです。以下のプログラムを実行するとコアダンプがでるので、解決法を教えて頂きたいです。 5つのdatファイルの読み込みはうまくいきました。15個に増やしたところ、コアダンプが表示されました。 ファイルポインタを使わずに実行してみたら15個でも大丈夫でしたので、ファイルポインタが原因かと思います。 typedef struct{ int class; int** matrix; }pattern_struct; int main(int argc,char* argv[]) { pattern_struct *learn; FILE *fp; int width,height; int i,j,k,value; learn=(int*)malloc(argc*sizeof(int)); //ファイルからの学習データの読み込み for(k=1;k<argc;k++){ fp=fopen(argv[k],"r"); printf("%s\n",argv[k]); printf("学習する数字を入力してください "); scanf("%d",&learn[k].class); fscanf(fp,"%d %d",&width,&height); learn[k].matrix=(int**)malloc(height*sizeof(int*)); for(i=0;i<height;i++) learn[k].matrix[i]=(int*)malloc(width*sizeof(int)); for(i=0;i<height;i++){ for(j=0;j<width;j++){ fscanf(fp,"%d",&value); learn[k].matrix[i][j]=value; } } fclose(fp); fp=NULL; } return 0; }

  • QNo.4191217 ライブラリ関数について教えてくださいの質問をした者です。

    質問を連投するのは気が引けたのですが、 どうしても分からなかったのでまた質問させてください・・・ ファイルの中のデータと配列データが一致するかを調べるプログラムを作ろうとしています。 前質問で、ライブラリ関数について教えていただき 以下のようにプログラムを作成してみました。 しかし、これだと結果が何も出力されませんでした・・・ 何が間違っていて、どうすればいいのか詳しく教えていただけないでしょうか。 よろしくお願いします。 #include<stdio.h> struct test { char no[5]; char name[10]; char english[5]; char math[5]; }; int main(void){ FILE *fp; int i; char f_no[5], f_name[5]; struct test data[5] = { {"001","akemi","100","40"}, {"002","tadao","59","76"}, {"003","mika","94","69"}, {"004","hiroshi","54","98"}, {"005","kazu","39","57"} }; struct test *test_p; test_p = data; if ((fp = fopen("test.txt", "r")) == NULL) { printf("NOT OPEN FILE\n"); } else { while (fscanf(fp, "%s%s", f_no, f_name) == 2) { for(i = 0; i<=5; i++) { if((strcmp(test_p->no,f_no)==0) && (strcmp(test_p->name,f_name)==0) { printf("%s %s 英語%s 数学%sです。\n", f_no, f_name, test_p->english, test_p->math); } else { printf("%s %s 一致しません\n", f_no, f_name); break; } ++test_p; } } } fclose(fp); } test.txtの中身 001 akemi 002 kazuo 003 tadashi 005 mika 006 xxx

  • なんらかの原因でtxtにデータを入力できない

    こんにちは。 C言語初心者です。 まずこのようなデータを用意しました。 kus1.txt 89 65 37 44 51 30 20 10 そして、このようなプログラムをし、ビルトしました。 #include <stdio.h> #define NUM 8 int main(void) { FILE *fp; int kusa[NUM]; int max,min; int i,k; fp = fopen("kus1.txt","r"); if(fp == NULL){ printf("ファイルオープン失敗\n"); return 1; } for(i=0; i<NUM; i++){ fscanf(fp, "%d", &kusa[i]); } max = kusa[0]; min = kusa[0]; for(k=0; k<NUM; k++){ if(max < kusa[k]) max = kusa[k]; if(min > kusa[k]) min = kusa[k]; printf("NO.%-5d%d\n", k+1, kusa[k]); } printf("最高は%d。\n", max); printf("最低は%d。\n", min); fclose(fp); return 0; } その後、コマンドプロンプトでこれを実行したところ、 ファイルオープン失敗 とでてきました。つまりなんらかの原因で失敗しました。 どうしたら成功できるのでしょうか。教えてください。