dポイントプレゼントキャンペーン実施中!

malloc関数を使いメモリを確保しそこへ"ABCD"と記憶させ、ポインタ*Cを使い確保したメモリの内容を表示するプログラムです。

*********************************************
#include <stdio.h>
#include <stdlib.h>

int main(void)
{
  int i;
  char *C;

  C = (char *) malloc (sizeof(char) * 5);

  C = "ABCD";

  for(i = 0; i < 5; i++){
    if(C[i] != NULL){
      printf("%s", C[i]);    ←※エラー※
    }
  }

  free(C);

  return 0;
}
*********************************************

正常にコンパイルできますが実行エラーになります。VCを使いF10のデバッグテストで※のところエラーになります。なぜなのでしょうか?

A 回答 (2件)

C[i] は、char で、%s の要求するchar * ではないから。



あと、
C = (char *) malloc (sizeof(char) * 5);
で確保したメモリに文字列を設定するには、
strcpy (または、strncpy,stpcpy)を使います。
C = "ABCD";
したら
free(C) は、malloc で確保したのとは違う領域を開放しようとしてエラーになります。(アドレスの代入によって、確保した領域はアクセスできなくなります)
printf で文字列を表示するなら
printf("%s", C);

1文字ずつ表示するなら
printf("%c",C[i]);
でします。
    • good
    • 0
この回答へのお礼

ご返答ありがとうございます。
strcpy関数を使えば良いという事だけではなく、内部的な動きまで丁寧に教えていただきとても理解できました。おかげで実行できました。

お礼日時:2006/09/27 04:28

> C = (char *) malloc (sizeof(char) * 5);


ここでポインタ変数Cに、mallocで確保した領域へのポインタが代入されていますが、

> C = "ABCD";
ここで文字列リテラル"ABCD"を指すものに上書きされています。
結果として、mallocで確保した領域へのポインタが分からなくなってしまったので、
後でfreeで開放することができなくなります。(メモリリーク)

> C[i] != NULL
C[0]やC[1]は、ここでは'A'や'B'などの文字なので
ポインタであるNULLと比較するのはおかしいです。
文字である'\0'と比較したほうが意味が通ります。
 C[i] != '\0'

> printf("%s", C[i]);
先に書いたように、C[i]は文字なので、
文字列(実際は文字列の先頭文字へのポインタ)を要求する%sと合わせて使うとおかしな結果になります。
(エラーの直接の原因はこれでしょう。)
 printf("%c", C[i]);
もしくはループさせずに
 printf("%s", C);
とするべきです。

> free(C);
先に書いたように、Cはこの時点で文字列リテラル"ABCD"を指しているので、
freeすると問題が発生するかもしれません。
    • good
    • 0
この回答へのお礼

ご返答ありがとうございます。
No,1様の回答にはなかった他の箇所の指摘と動きの説明までしていただき、とても理解できました。おかげで実行できるようになりました。

お礼日時:2006/09/27 04:36

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!