calloc()関数について

フォーラム(掲示板)ルール
フォーラム(掲示板)ルールはこちら  ※コードを貼り付ける場合は [code][/code] で囲って下さい。詳しくはこちら
たまひよ

calloc()関数について

#1

投稿記事 by たまひよ » 17年前

BMPファイルのXサイズ分をCallocで取り、別のファイルにそのまま書き込ませ、
ちゃんと書けたか確認(実際は書けていなかったのですが)しようとしたのですが
上手くいきませんでした。
分からない点は、
freadして fwriteしたの所が読んだ物をそのまま書けていない点。
表示の所でcallo_mem[a]という使い方で中身が表示出来ない点です

どなたかお力を貸して下さい
int temp_gara_make(u_int x_size,u_int y_size)
{
long plus = 0;
u_int amari;
u_int i;
u_int a;
char *callo_mem;

   if ((T_fp = fopen(T_File,"ab")) == 0)	{    /* Temp file */
	printf("\nTemp_File_Open_Error!!\n");
	return 100;
   }
   if ((BMP_fp = fopen(B_File,"rb")) == 0)	{    /* BMP file */
	printf("\n BMP_File_Open_Error2!!\n");
	return 200;
   }
   else	{
	fseek(BMP_fp,B_str_p,SEEK_SET);           /* B_str_p = BMP画像書出し位置 */
 	callo_mem = (char *)calloc(x_size,sizeof(char))	;
	if(callo_mem == 0)	{
		printf("\nメモリの確保が出来ません");
		free(callo_mem);
	}
	else	{
		fseek(T_fp,0,SEEK_END);
		for(i=1; i<=y_size; i++)	{
			fread(callo_mem,x_size,1,BMP_fp); 
			fwrite(callo_mem,x_size,1,T_fp);
		
		         for(a = 0; a<x_size; a++)	{
			        printf("%d:%d",a,callo_mem[a]);
		         }
		         amari = x_size % 4;
		         switch(amari)	{
			        case 1:
				        plus = plus + x_size + 3;
				        break;
			        case 2:
				        plus = plus + x_size + 2;
				        break;
			        case 3:
				        plus = plus + x_size + 1;
				        break;
			        case 0:
				        plus = plus + x_size;
				        break;
			        default:
				        printf("\n間違った計算結果です");
				        break;
		        }
		        plus = B_str_p + plus;       /* plus = 次の画像開始位置*/
		        fseek(BMP_fp,plus,SEEK_SET);
		        fseek(T_fp,plus,SEEK_SET);
	         }
	         printf("\ntemp_make    書き込み終了\n");
	         free(callo_mem);	
         }
  }
  fclose(BMP_fp);
  fclose(T_fp);

}

toyo

Re:calloc()関数について

#2

投稿記事 by toyo » 17年前

とりあえず気づいた点
"a"モードで開いたファイルはfseekしても意味がないです
常にファイルの末尾に書き込まれます
"w"モードで開いてもファイルエンドより後にはfseekできないので
fseek(T_fp,plus,SEEK_SET);
は役に立ってないでしょう。
int padding = 0;
とでもしておいて
fwrite(&padding, 1, amari, T_fp);
で良いのでは。

toyo

Re:calloc()関数について

#3

投稿記事 by toyo » 17年前

あらかじめx_sizeを4バイト境界に揃えておく手もあります
かなりすっきりになります。
#define ALIGN_MASK (0xFFFFFFFC)
int temp_gara_make(u_int x_size, u_int y_size)
{
	u_int i;
	u_int a;
	char *callo_mem;

	x_size += 3;
	x_size &= ALIGN_MASK;
	if ((T_fp = fopen(T_File,"ab")) == NULL)	{    /* Temp file */
		printf("\nTemp_File_Open_Error!!\n");
		return 100;
	}
	if ((BMP_fp = fopen(B_File,"rb")) == NULL)	{    /* BMP file */
		printf("\n BMP_File_Open_Error2!!\n");
		return 200;
	}
	else	{
		fseek(BMP_fp, B_str_p, SEEK_SET);           /* B_str_p = BMP画像書出し位置 */
 		callo_mem = (char *)calloc(x_size, sizeof(char))	;
		if(callo_mem == NULL)	{
			printf("\nメモリの確保が出来ません");
			free(callo_mem);
		}
		else {
			for(i = 1; i <= y_size; i++)	{
				fread(callo_mem, 1, x_size,BMP_fp); 
				fwrite(callo_mem, 1, x_size,T_fp);
				
				for(a = 0; a < x_size; a++)	{
					printf("%d:%hhd", a, callo_mem[a]);
				}
			}
			printf("\ntemp_make    書き込み終了\n");
	    	free(callo_mem);	
		}
  	}
	fclose(BMP_fp);
	fclose(T_fp);
	return 0;
}
ところでBMPは8ビットカラー限定ですよね

たまひよ

Re:calloc()関数について

#4

投稿記事 by たまひよ » 17年前

toyo様
ご回答ありがとうございます。

>"a"モードで開いたファイルはfseekしても意味がないです
そうですよね。とても恥ずかしいミスです。
しかも、T_fpは移動する必要が無かったので、"a"モードで開いているのに・・・。
完全に勘違いです。

ご指摘ありがとうございました。

>ところでBMPは8ビットカラー限定ですよね
はい。8ビットのカラーを別の画像用のデータに書き換える為のプログラムです。
BMPの4バイトがあまりの数分、書き換え後不要になるので、その部分を飛ばす為に
swichを作っています。
なのでT_fpのseekが無意味になるんです(--; ←何度書いても恥ずかしいです。

fread(callo_mem, 1, x_size,BMP_fp);
fwrite(callo_mem, 1, x_size,T_fp);
の所は書き方的には間違ってないんですね
上手く書き換わってなかったのは別の理由からみたいなので、もう少し考えてみます。

printf("%d:%hhd", a, callo_mem[a]);
この部分の「%hhd」というのはどういう表示になるのでしょう?

toyo

Re:calloc()関数について

#5

投稿記事 by toyo » 17年前

>printf("%d:%hhd", a, callo_mem[a]);
>この部分の「%hhd」というのはどういう表示になるのでしょう?

整数のフォーマット指定子はデフォルトが int 型になります。
これにhをつけるとshort型にhhをつけるとchar型になります。
callo_memはchar型なのでhhをつけました。
16進数2桁で表示する場合は
printf("%d:%02hhX", a, callo_mem[a]);
というふうになります。
逆にlong型ではlをlong long型ではllをつけます。
つけなくても警告出ないコンパイラが多いのですが私はつけるようにしています。

たまひよ

Re:calloc()関数について

#6

投稿記事 by たまひよ » 17年前

toyo様
ご回答ありがとうございます。

>整数のフォーマット指定子はデフォルトが int 型になります。
>これにhをつけるとshort型にhhをつけるとchar型になります。
16進数の2桁の「%02」は知っていましたが、「h」や「hh」は勉強不足で知りませんでした。

表示用のキャストみたいな感じなんですね。
勉強になりました。
今度から使ってみます。

そう言えば、lのみの時は使った事がありました。(今更遅いですが)

callokの件は間違っていなかったのでこのまま頑張ってみます

閉鎖

“C言語何でも質問掲示板” へ戻る