以下のコードを実行すると、答えとしてそれぞれ 3 と 36 が得られました。
x ="abd"
print len(x)
print sys.getsizeof(x)
誰かが私にそれらの違いを説明できますか?
以下のコードを実行すると、答えとしてそれぞれ 3 と 36 が得られました。
x ="abd"
print len(x)
print sys.getsizeof(x)
誰かが私にそれらの違いを説明できますか?
それらはまったく同じものではありません。
len()
コンテナーに含まれるアイテムの数を照会します。文字数の文字列の場合:
オブジェクトの長さ (アイテムの数) を返します。引数は、シーケンス (文字列、タプル、またはリスト) またはマッピング (辞書) です。
sys.getsizeof()
一方、オブジェクトのメモリ サイズを返します。
オブジェクトのサイズをバイト単位で返します。オブジェクトは、任意のタイプのオブジェクトにすることができます。すべての組み込みオブジェクトは正しい結果を返しますが、これは実装固有であるため、サードパーティの拡張機能に当てはまるとは限りません。
Python 文字列オブジェクトは、1 文字あたり 1 バイトの単純な文字列ではありません。
具体的にsys.getsizeof()
は、ガベージ コレクターのオーバーヘッドがあれば関数に含めます。
getsizeof()
オブジェクトのメソッドを呼び出し、オブジェクト__sizeof__
がガベージ コレクターによって管理されている場合は、ガベージ コレクターのオーバーヘッドを追加します。
文字列オブジェクトを追跡する必要はありません (循環参照を作成することはできません) が、文字列オブジェクトは 1 文字あたりのバイト数よりも多くのメモリを必要とします。Python 2 では、__sizeof__
メソッドは (C コードで) を返します。
Py_ssize_t res;
res = PyStringObject_SIZE + PyString_GET_SIZE(v) * Py_TYPE(v)->tp_itemsize;
return PyInt_FromSsize_t(res);
ここPyStringObject_SIZE
で、 は型の C 構造体ヘッダー サイズです。PyString_GET_SIZE
基本的には と同じlen()
でPy_TYPE(v)->tp_itemsize
、1 文字あたりのサイズです。Python 2.7 では、バイト文字列の場合、1 文字あたりのサイズは 1 ですが、それPyStringObject_SIZE
が混乱を招きます。私の Mac では、そのサイズは 37 バイトです。
>>> sys.getsizeof('')
37
文字列の場合unicode
、1 文字あたりのサイズは最大 2 または 4 になります (コンパイル オプションによって異なります)。Python 3.3 以降では、文字列の内容に応じて、Unicode 文字列は 1 文字あたり 1 ~ 4 バイトを占めます。