• ベストアンサー

ポインタの文字の代入について

素朴な疑問ですが、なぜ宣言文の時には*ptrに文字列を代入してもエラーが出ないのに、宣言文以外のところで下記の記述をするとエラーが出るのですか? #include<stdio.h> void main(void) { char *ptr = "DEF"; *ptr = "ABC";//コンパイルエラー      ptr = "ABC";//正常 }

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

  • ベストアンサー
  • liar_adan
  • ベストアンサー率48% (730/1515)
回答No.3

>宣言文の時には*ptrに文字列を代入してもエラーが出ない わけではないのです。 こう考えて下さい。 char *ptr; は char 「*ptr」; ではなく 「char *」 ptr; つまり「charへのポインタ」として「prt」を宣言したわけです。 ここで宣言されたのは「ptr」です。「*prt」ではありません。 一方、下の方に出てくる「*ptr」は「prt」に「*」をつけたものです。 ptrに*をつけると、char型の変数となります。 しかし、右側"ABC"の型は「char型」ではなくて「char型へのポインタ型」です。 型が合わなくてエラーになります。 細かいことを言います。 宣言のところで使われる「*」は、「ポインタ宣言子」といいます。 下の式のところで使われる「*」は「間接参照演算子」です。 つまり同じ「*」でも、違うものなのです。 これは、Cの宣言方法のわかりにくさにも責任があります。 ただもう直せないので、こういうものだと覚えて下さい。

yukikundesuyo
質問者

お礼

ポインタ宣言子と間接参照演算子という言葉は始めてききました。大変参考になりました。

その他の回答 (2)

  • sha-girl
  • ベストアンサー率52% (430/816)
回答No.2

x = "ABC"は文字列「ABC」を確保したアドレスをxに代入します。 一方t*ptr = xはアドレスptrにxを置こうとします。 つまり*ptr = 'A'とかなら 通ります。 *prtに格納できるのは1バイトの文字(char)です。 *ptr = 'A' *(ptr+1) = 'B' *(ptr+2) = 'C' *(ptr+3) = '\0' ならokです。 >*ptr = "ABC";//コンパイルエラー は*ptrにアドレス(普通4バイト)を格納しようとするからです。

noname#240783
noname#240783
回答No.1

宣言文における * は、あくまで 変数ptr がポインタであることを 示しているだけです。 つまり、char *ptr = "DEF"; 文は、 char型のポインタ変数 ptr を宣言し、 メモリ上に"DEF"という文字列を格納した領域が確保され、 その先頭アドレスをポインタ変数 ptr に「代入」しています。 しかし、*ptr = "ABC"; 文における * は「間接参照子」ですから、 ポインタ変数 ptr に格納されているアドレスが指し示す メモリ上にある内容を「参照」することしか出来ません。 さらにしかし、ptr = "ABC"; では、メモリ上のどこかに確保された 文字列 "ABC" の領域の先頭アドレスを、ポインタ変数に「代入」する結果に なるのでコンパイルが通る、のだと思います。

関連するQ&A