こんにちはゲストさん。会員登録(無料)して質問・回答してみよう!

解決済みの質問

C 動的メモリ確保後のファイルへの書き込みについて

■プログラムの目的。
入力したデータをCSV形式でファイルに出力。

■プログラムの問題と質問内容。
realloc関数でメモリを再度割り当てると、入力したデータをファイルに出力できません。

ですが、再度割り当て前に入力処理を終了するとファイルに出力できます。
なんとなく原因は、realloc関数の扱い方の問題であることはわかるんですが
どこを修正すればいいのかわかりません。
教えてください。よろしくお願いします。

■プログラムのソース
#include<stdio.h>
#include<stdlib.h>
#define DATASIZE 3

typedef struct{
char str[10];
}CONS;

void Input_data(CONS *data)
{
gets(data->str);
return;
}

void Output_display(CONS *data)
{
puts(data->str);
return;
}

void Write_data(CONS *data,int count)
{
FILE *fp;
char fname[]="data.csv";
int i;

if( (fp = fopen(fname,"w")) == NULL ){
puts("fopen error");
exit(1);
}

/* write data */
for(i=0; i<=count; i++){
if(data[i].str[0] == '\0') break;
fprintf(fp,"%d,%s\n", i, data[i].str);
fprintf(stdout,"%d,%s\n", i, data[i].str);
}

fclose(fp);
return;
}

int main(void)
{
CONS *data,*data_temp;
int data_size = DATASIZE;
int i,count;

if( (data=(CONS *)malloc(sizeof(CONS)*DATASIZE)) == NULL){
puts("malloc error");
exit(1);
}

/* Input data */
puts("-- input_data");
for(i=0; ; i++){
count = i;

/* Realloc */
if( count == data_size ){
if( (data_temp=(CONS *)realloc(data,sizeof(CONS)*DATASIZE)) == NULL){
free(data);
puts("realloc error");
exit(1);
}else{
data = data_temp;
data_size += DATASIZE;
puts("** realloc");
}
}
/* end of Realloc */

printf("%2d,",i);
Input_data(data+i);
if(data[i].str[0] == '\0'){
puts("-- end of input_data\n");
break;
}
}
/* end of Input_data */

/* Output_display */
puts("-- output_display");
for(i=0; i<=count; i++){
printf("%2d,",i);
Output_display(data+i);
}
/* end of Output_display */

/* Write_data */
puts("-- Write_data");
Write_data(data,count);
/* end of Write_data */

free(data);
return 0;
}

投稿日時 - 2010-11-13 22:28:46

QNo.6317479

困ってます

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

realloc関数の第二引数は追加割り当てサイズではなく、再割り当て前のメモリを含めた全サイズです。この辺を勘違いしていると思われます。
mallocとreallocでメモリサイズが同じですが、これが間違っているのではないでしょう?

投稿日時 - 2010-11-13 23:04:15

お礼

ご回答ありがとうございます!下記のソースに修正したところ無事に動作しました。
回答者様のご指摘どおりで、『追加割り当て』と『再割り当て』を勘違いしていたのが原因でした。
また質問をご覧の皆様に、質問分にあるソースをコンパイルして実行後、realloc関数が働くとエラーになるので、どうか実行しないようにお願いいたします。申し訳ありません。

if( (data_temp=(CONS *)realloc( data,sizeof(CONS) * (DATASIZE+data_size) )) == NULL){
 free(data);
 puts("realloc error");
 exit(1);
}else{
 data = data_temp;
 data_size += DATASIZE;
 puts("** realloc");
}

投稿日時 - 2010-11-13 23:42:23

このQ&Aは役に立ちましたか?

0人が「このQ&Aが役に立った」と投票しています

回答(1)

あなたにオススメの質問