文字列のメモリ保持期間とポインタについてわからないので教えてください。
よくポインタの説明に、文字列を使った下記のようなサンプルコードが紹介されます。
char* s;
s = "abcdefg";
printf("%s",s);
(http://www2.netf.org/pointer3.html から引用)
この"abcdefg"により確保された領域がいつまで保持されるのかわかりません。
・これを実行しているメソッドを抜けるまでなのか?
・free(s)するまでなのか?(free(s)しなければいけないのか?)
この例だとprintfして終わっていますが、sを戻り値として返却して他で利用したり、オブジェクトを生成して、そのメンバ変数に
obj1->field1 = "value";
というように格納して利用することとか考えると、領域は勝手に開放されず、やっぱり明示的にfreeするということでしょうか?
freeしないといけない、なんて記述も見たことがなくよく理解できずにいます。
よろしくお願いします。
No.2ベストアンサー
- 回答日時:
場合によります。
>char* s;
>s = "abcdefg";
>この"abcdefg"により確保された領域がいつまで保持されるのかわかりません。
>・これを実行しているメソッドを抜けるまでなのか?
>・free(s)するまでなのか?(free(s)しなければいけないのか?)
この場合は、プログラムがメモリにロードされた時点でメモリ上に"abcdefg"が配置され、
その先頭アドレスを char型のポインタ変数sに代入しているだけです。
# 「文字列リラテル」で検索されるとよいでしょう。
で、メモリ上に配置され"abcdefg"は、プログラムが終了するまで有効ですから解放する必要はありません。
# ちなみに「定数」扱いになりますので普通は書き換えできません。
>オブジェクトを生成して、そのメンバ変数に
>obj1->field1 = "value";
>というように格納して利用する
実装にもよりますが…たいていクラス内で「内容を変更する」必要がある場合は、領域を確保して「コピー」しているかと。
free()が必要なのは、malloc()やcalloc()等で明示的に確保した場合…になります。
標準関数でどの程度あるかは不明ですが…
「呼び出し元が解放の責任を負う」という作りの関数を使用した場合は、当然free()は必要ですが。
# strdup()とか。
ダブルクォートで作成した文字列は静的な定数として扱うんですね。
文字列の内容を変更するような場合には、メモリを確保してそこに内容をコピーしてから使用するというのは初耳でした。
No.3
- 回答日時:
> この"abcdefg"により確保された領域がいつまで保持されるのかわかりません。
"abcdefg"は文字列リテラルとしてソースコードに直書きされています。
こういうものはプログラムがメモリ上にロードされた時に、静的なメモリ空間に割り当てられます。
(PCだと実行時にRAM上にロードされますが、マイコン用の組み込みソフトなどではROM上のメモリ空間に割り当てられることもあります)
したがって、このメモリ領域はプログラムが実行された時から終了するまで保持されます。
もっとも、"abcdefg"はずっと存在しますが、それを指してるポインタ変数「s」はローカル変数なので、関数を抜けた時点で消滅します。(static宣言されている場合は別ですが)
そういうわけで、関数の戻り値で他に渡しても構いませんし、free()する必要はありません。
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
似たような質問が見つかりました
- C言語・C++・C# C言語初心者 構造体 課題について 2 2023/03/10 19:48
- その他(プログラミング・Web制作) pythonのプログラムについての質問です。 1 2023/05/26 10:31
- C言語・C++・C# C言語の質問です。 以下の命令を実行するプログラムを作りました ①文字列aとbの長さを表示 ②aとb 1 2022/04/29 15:35
- C言語・C++・C# ポインタの型変換、どうやるんでしたっけ? 2 2022/03/28 11:00
- C言語・C++・C# 宣言する関数の形が決まっている状態で、 str1とstr2の文字列をこの順に引っ付けてstrに保存し 2 2022/05/30 18:21
- C言語・C++・C# 関数ポインタの高速化のメリット 7 2023/05/05 20:15
- C言語・C++・C# sprintf()の使い方について 1 2022/08/17 16:16
- C言語・C++・C# c言語 コマンドライン引数 4 2023/02/09 18:47
- C言語・C++・C# const char** p;のとき、free(p)でC4090エラーとなるのはなぜですか 3 2023/03/31 16:28
- Visual Basic(VBA) 以下のVBAで該当文字列の前後に付与したい。 例 前に付与 abc ユーザーID 12345 後に付 3 2022/04/19 21:50
関連するカテゴリからQ&Aを探す
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
指定したメモリアドレスの値の...
-
MFCのCStringについて
-
newしないオブジェクトについて
-
C++で、メンバもヒープに確保さ...
-
GetCommandLineを使用しました。
-
malloc呼び出し時のセグメンテ...
-
mallocについて
-
ヒープメモリの解放について
-
プログラムが途中で強制終了し...
-
LPTSTR型の変数に文字を格納
-
構造体のメモリ確保のキャスト...
-
テキストファイルを二次元配列に
-
16進ダンプのプログラム
-
2次元配列の動的確保について
-
確保という言葉の使い方について
-
構造体配列の初期化について
-
構造体リストの使い方について
-
自作のstrcatが動かない件
-
アンマネージド関数でのメモリ...
-
new領域確保について
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
c言語のポインタへの文字列入力...
-
mallocについて
-
newしないオブジェクトについて
-
allocってなんですか?
-
配列の添え字の最大数とは?
-
ヒープメモリの解放について
-
プログラムが途中で強制終了し...
-
Accessで、メモリを開放するタ...
-
malloc呼び出し時のセグメンテ...
-
ビットをローテートするプログ...
-
C++で、メンバもヒープに確保さ...
-
void*型のデータサイズ
-
入れ子になった構造体について
-
C言語に関する質問
-
スタック破壊の上手な見つけ方...
-
mallocで確保するメモリの領域...
-
C++のnewで確保したメモリーの...
-
指定したメモリアドレスの値の...
-
ヒープ領域の限界値設定
-
構造体でchar name[]と*nameの...
おすすめ情報