- ベストアンサー
strcpy関数で文字型変数へのポインタを指定するとエラーになる
(1)のコードは問題なく動作するのですが、(2)の方はバスエラーとなります。どちらもも引数としてアドレスを渡しているのに何が違うのでしょうか? (1) char ch[]="aaaa"; strcpy(ch, "bbbb"); printf("%s\n", ch); (2) char *chp="xxxx"; strcpy(chp, "yyyy"); printf("%s\n", chp);
- みんなの回答 (5)
- 専門家の回答
質問者が選んだベストアンサー
バスエラーの原因は#1で出ている通りですが、環境によっては文字列リテラルを書き換え可能領域に配置するものがあり、そのような環境では#4で言われているようにバスエラーを起こさずに通ってしまいます。 > char *chp="xxxx"; > chp="yyyy"; これがエラーにならないのは「文字列chpの中身を書き換えている」のではなく、「ポインタ変数chpが指す先を"xxxx"から"yyyy"に変更している」からです。 ポインタの代入とstrcpy()は等価動作ではありません。
その他の回答 (4)
- xceu
- ベストアンサー率25% (2/8)
1) char ch[]="aaaa"; //文字配列の領域をプログラムで確保している。 strcpy(ch, "bbbb"); printf("%s\n", ch); (2) char *chp="xxxx"; //*chpは"xxxx"をさしているポインタにすぎない。 strcpy(chp, "yyyy"); //"xxxx"の領域はコンパイラが確保した。 printf("%s\n", chp); //その領域はメモリの不定な場所かも・・ //chpはその不定な領域を参照(ポイント)・・ char ch[]="xxxx"; char *chp=ch; //この方が「安全」 strcpy(chp,"yyyy"); printf("%s\n",chp); (2)は処理系によっては通る場合もありますよ。
- yaemon_2006
- ベストアンサー率22% (50/220)
ごめん。No2は間違い。
- yaemon_2006
- ベストアンサー率22% (50/220)
(1)も(2)も問題あり。
- ChateauAres
- ベストアンサー率43% (64/148)
(1)のchは書換え可能なメモリ領域を取得するので問題ないです。 (2)の"xxxx"は書換え不可能な定数エリアのようなメモリ領域が取得されます。 よって書換えできない領域を書換えしようとして、バスエラーになります。
補足
char *chp="xxxx"; // strcpy(chp, "yyyy"); chp="yyyy"; printf("%s\n", chp); すみません。それでは、上記のように直接文字列を代入すると不可能な定数エリアでも書き換えられるのはなぜでしょうか?
お礼
なるほど (1)strcpyで本当にエリアを塗り替えてしまう (2)ポインタの指し位置を別の場所に変更しているに過ぎない(元の文字列は実はメモリ上残ったまま) という感じですかね。イメージが湧きました。有り難うございました。