3. データモデル¶
3.1. オブジェクト、値、および型¶
Python における オブジェクト (object) とは、データを抽象的に表したものです。Python プログラムにおけるデータは全て、オブジェクトまたはオブジェクト間の関係として表されます。(ある意味では、プログラムコードもまたオブジェクトとして表されます。これはフォン・ノイマン: Von Neumann の "プログラム記憶方式コンピュータ: stored program computer" のモデルに適合します。)
オブジェクトはアイデンティティ値 (identity) 、型 (type) 、そして値 (value) を持ちます。オブジェクトが一度生成されると、そのオブジェクトの アイデンティティ値 は決して変化することがありません; アイデンティティ値をオブジェクトのメモリ上のアドレスと考えてもかまいません。演算子 'is
' は、二つのオブジェクト間のアイデンティティ値を比較します; 関数 id()
は、オブジェクトのアイデンティティ値を表す整数 (現在の実装ではオブジェクトのメモリ上のアドレス) を返します。オブジェクトの 型 もまた変わることがありません。 1 オブジェクトの型は、そのオブジェクトのサポートする操作 ("長さを持っているか?" など) を決定し、その型のオブジェクトが取りうる値について定義しています。 type()
関数は、オブジェクトの型 (型自体も一つのオブジェクトです) を返します。オブジェクトによっては、 値 (value) を変えることができます。値を変えることができるオブジェクトは 変更可能 (mutable) であるといいます; 値を一度設定すると、その後は変えることができないオブジェクトは 変更不能 (immutable) であると呼びます。 (変更不能なコンテナオブジェクトが変更可能なオブジェクトへの参照を含んでいる場合、その値は後者のオブジェクトの変更によって変わる場合があります; その場合でも、コンテナの含んでいるオブジェクトの集まりは変わらないため、コンテナは変更不能と考えます。したがって、変更不能性 (immutability) は、厳密には変更できない値を持っていることとは違い、もっと微妙な概念です。) オブジェクトの変更可能性は型で決定されます; 例えば、数値、文字列、およびタプルは変更不能であり、辞書やリストは変更可能です。
オブジェクトを明示的に破壊することはできません; しかし、オブジェクトに到達不能 (unreachable) になると、ガベージコレクション (garbage-collection) によって処理されます。実装では、ごみ収集を遅らせたり、全く行わないようにすることができます --- 到達可能なオブジェクトをごみ収集処理してしまわないかぎり、どう実装するかは実装品質の問題です。
現在の CPython 実装では参照カウント(reference-counting) 方式を使っており、(オプションとして) 循環参照を行っているごみオブジェクトを遅延検出します。この実装ではほとんどのオブジェクトを到達不能になると同時に処理することができますが、循環参照を含むごみオブジェクトの収集が確実に行われるよう保証しているわけではありません。循環参照を持つごみオブジェクト収集の制御については、 gc
モジュールを参照してください。 CPython以外の実装は別の方式を使っており、CPythonも将来は別の方式を使うかもしれません。オブジェクトが到達不能になったときに即座に終了処理されることに頼らないでください (例えば、ファイルは必ず閉じてください)。
実装のトレース機能やデバッグ機能を使えば、通常は収集されてしまうようなオブジェクトを生かしておくことがあるので注意してください。また、 'try
...except
' 文を使って例外を捕捉できるようにすると、オブジェクトを生かしておくことがあります。
オブジェクトによっては、開かれたファイルやウィンドウといった、 "外部 (external) の" リソースに対する参照を行っています。これらのリソースは、オブジェクトがごみ収集された際に解放されるものと理解されていますが、ごみ収集が行われる保証はないので、こうしたオブジェクトでは外部リソースを明示的に解放する方法、大抵は close()
メソッドを提供しています。こうしたオブジェクトは明示的に close するよう強く奨めます。操作をする際には、'try
...finally
' 文を使うと便利です。
他のオブジェクトに対する参照をもつオブジェクトもあります; これらは コンテナ (container) と呼ばれます。コンテナオブジェクトの例として、タプル、リスト、および辞書が挙げられます。オブジェクトへの参照自体がコンテナの値の一部です。ほとんどの場合、コンテナの値というと、コンテナに入っているオブジェクトの値のことを指し、それらオブジェクトのアイデンティティではありません; しかしながら、コンテナの変更可能性について述べる場合、今まさにコンテナに入っているオブジェクトのアイデンティティのことを指します。したがって、 (タプルのように) 変更不能なオブジェクトが変更可能なオブジェクトへの参照を含む場合、その値が変化するのは変更可能なオブジェクトが変更された時、ということになります。
型はオブジェクトの動作のほとんど全てに影響します。オブジェクトのアイデンティティが重要かどうかでさえ、ある意味では型に左右されます: 変更不能な型では、新たな値を計算するような操作を行うと、実際には同じ型と値を持った既存のオブジェクトへの参照を返すことがありますが、変更可能なオブジェクトではそのような動作は起こりえません。例えば、 a = 1; b = 1
とすると、 a
と b
は値 1 を持つ同じオブジェクトを参照するときもあるし、そうでないときもあります。これは実装に依存します。しかし、 c = []; d = []
とすると、 c
と d
はそれぞれ二つの異なった、互いに一意な、新たに作成された空のリストを参照することが保証されています。 (c = d = []
とすると、 c
と d
の両方に同じオブジェクトを代入します)
3.2. 標準型の階層¶
以下は Python に組み込まれている型のリストです。(C、Java、または実装に使われているその他の言語で書かれた) 拡張モジュールでは、その他に新たな型を定義することができます。将来のバージョンの Python では、型の階層に新たな型 (整数を使って効率的に記憶される有理数型、など) を追加することができるかもしれません。
以下に説明する型のいくつかには、'特殊属性 (special attribute)' と題された段落が連ねられています。これらの属性は実装へのアクセス手段を提供するもので、一般的な用途に利用するためのものではありません。特殊属性の定義は将来変更される可能性があります。
- None
この型には単一の値しかありません。この値を持つオブジェクトはただ一つしか存在しません。このオブジェクトは組み込み名
None
でアクセスされます。このオブジェクトは、様々な状況で値が存在しないことをしめします。例えば、明示的に値を返さない関数はNone
を返します。None
の真値 (truth value) は偽 (false) です。- NotImplemented
この型には単一の値しかありません。この値を持つオブジェクトはただ一つしか存在しません。このオブジェクトは組み込み名
NotImplemented
でアクセスされます。数値演算に関するメソッドや拡張比較 (rich comparison) メソッドは、被演算子が該当する演算を行うための実装をもたない場合、この値を返すことがあります。(演算子によっては、インタプリタが関連のある演算を試したり、他の代替操作を行います。) 真値は真 (true) です。- Ellipsis
この型には単一の値しかありません。この値を持つオブジェクトはただ一つしか存在しません。このオブジェクトは組み込み名
Ellipsis
でアクセスされます。スライス内に...
構文がある場合に使われます。真値は真 (true)です。numbers.Number
数値リテラルによって作成されたり、算術演算や組み込みの算術関数によって返されるオブジェクトです。数値オブジェクトは変更不能です; 一度値が生成されると、二度と変更されることはありません。Python の数値オブジェクトはいうまでもなく数学で言うところの数値と強く関係していますが、コンピュータ内で数値を表現する際に伴う制限を受けています。
Python は整数、浮動小数点数、複素数の間で区別を行っています:
numbers.Integral
(整数)整数型は、整数(正の数および負の数)を表す数学的集合内における要素を表現する型です。
以下に三つの整数型を示します:
- (通常の) 整数型 (plain integer)
-2147483648 から 2147483647 までの整数を表現します (基本ワードサイズ: natural word size がより大きなマシンではより大きな定義域になることもあります。より小さくなることはありません。) 演算の結果が定義域を超えた値になった場合、結果は通常長整数で返されます (場合によっては、
OverflowError
が送出されます) 。シフト演算やマスク演算のために、整数は 32 ビット以上の 2 の補数で表されたバイナリ表現を持つ (すなわち、4294967296 の異なったビットパターン全てが異なる値を持つ) と仮定されています。- 長整数型 (long integer)
長整数は無限の定義域を持ち、利用可能な (仮想) メモリサイズの制限のみをうけます。長整数はシフト演算やマスク演算のためにバイナリ表現をもつものと仮定されます。負の数は符号ビットが左に無限に延びているような錯覚を与える 2 の補数表現の変型で表されます。
- ブール型 (boolean)
真偽値の False と True を表します。
False
とTrue
を表す 2 つのオブジェクトのみがブール値オブジェクトです。ブール型は整数型の部分型であり、ほとんどの状況でそれぞれ 0 と 1 のように振る舞いますが、例外として文字列に変換されたときはそれぞれ"False"
および"True"
という文字列が返されます。
整数表現に関する規則は、シフト演算やマスク演算において、負の整数も含めて最も有意義な解釈ができるように、かつ通常の整数と長整数との間で定義域を切り替える際にできるだけ混乱しないように決められています。すべての演算で、演算結果がオーバフローを起こさずに整数の定義域の値になる場合は、長整数を使った場合でも、被演算子に整数と長整数を混合した場合でも同じ結果になります。定義域の切り替えはプログラマに対して透過的に(意識させることなく)行われます。
numbers.Real
(float
) (実数)この型は計算機レベルの倍精度浮動小数点数を表現します。表現可能な値の範囲やオーバーフローの扱いは計算機のアーキテクチャ(および、CやJavaによる実装)に従います。Pythonは単精度浮動小数点数をサポートしません。一般的に単精度浮動小数点数を使う理由はプロセッサーとメモリの使用を節約するためと説明されます。しかし、こうした節約はPythonでオブジェクトを扱う際のオーバーヘッドに比べれば微々たるものです。また、2種類の浮動小数点数型を持つことで複雑になる理由はありません。
numbers.Complex
(複素数)この型は、計算機レベルで倍精度とされている浮動小数点を 2 つ一組にして複素数を表現します。浮動小数点について述べたのと同じ性質が当てはまります。複素数
z
の実数部および虚数部は、それぞれ読み出し専用属性z.real
およびz.imag
で取り出すことができます。
- シーケンス型 (sequence)
この型は、有限の順序集合 (ordered set) を表現します。要素は非負の整数でインデクス化されています。組み込み関数
len()
を使うと、シーケンスの要素数を返します。シーケンスの長さが n の場合、インデクスは 0, 1, ..., n -1 からなる集合です。シーケンス a の要素 i はa[i]
で選択します。シーケンスはスライス操作 (slice) もサポートしています:
a[i:j]
とすると、 i<=
k<
j であるインデクス k をもつ全ての要素を選択します。式表現としてスライスを用いた場合、スライスは同じ型をもつ新たなシーケンスを表します。新たなシーケンス内では、インデクス集合が 0 から始まるようにインデクスの値を振りなおします。シーケンスによっては、第三の "ステップ (step)" パラメタを持つ "拡張スライス (extended slice)" もサポートしています:
a[i:j:k]
は、x = i + n*k
, n>=
0
かつ i<=
x<
j であるようなインデクス x を持つような a 全ての要素を選択します。シーケンスは、変更可能なものか、そうでないかで区別されています:
- 変更不能なシーケンス (immutable sequence)
変更不能なシーケンス型のオブジェクトは、一度生成されるとその値を変更することができません。 (オブジェクトに他のオブジェクトへの参照が入っている場合、参照されているオブジェクトは変更可能なオブジェクトでもよく、その値は変更される可能性があります; しかし、変更不能なオブジェクトが直接参照しているオブジェクトの集合自体は、変更することができません。)
以下の型は変更不能なシーケンス型です:
- 文字列型 (string)
文字列の各要素は文字 (character) です。文字型 (character type) は存在しません。単一の文字は、要素が一つだけの文字列として表現されます。各文字は(少なくとも)8-bit の 1 byte を表現します。組み込み関数
chr()
およびord()
を使うと、文字と非負の整数で表されたバイト値の間で変換を行えます。0--127 の値を持つバイト値は、通常同じ ASCII 値をもつ文字を表現していますが、値をどう解釈するかはプログラムにゆだねられています。文字列データ型はまた、例えばファイルから読み出されたデータを記憶するといった用途で、バイト値のアレイを表現するために用いられます。(ネイティブの文字セットが ASCIIでないシステムでは、
chr()
やord()
が ASCII と EBCDIC との間で対応付けを行っており、文字列間の比較で ASCII 順が守られる限り、文字列の内部表現として EBCDIC を使ってもかまいません。誰か他にもっとましなルールをお持ちですか?)- Unicode 文字列型
Unicode オブジェクトの各要素は Unicode コード単位です。 Unicode コード単位とは、単一の Unicode オブジェクトで、Unicode 序数を表現する 16-bit または 32-bit の値を保持できるものです (この序数の最大値は
sys.maxunicode
で与えられており、コンパイル時に Python がどう設定されているかに依存します)。 Unicode オブジェクト内にサロゲートペア (surrogate pair) があってもよく、Python はサロゲートペアを二つの別々の Unicode 要素として報告します。組み込み関数unichr()
およびord()
は、コード単位と非負の整数で表された Unicode 標準 3.0 で定義された Unicode 序数との間で変換を行います。他の文字エンコード形式との相互変換は、 Unicode メソッドencode()
および組み込み関数unicode()
で行うことができます。- タプル型 (tuple)
タプルの要素は任意の Python オブジェクトです。二つ以上の要素からなるタプルは、個々の要素を表現する式をカンマで区切って構成します。単一の要素からなるタプル (単集合 'singleton') を作るには、要素を表現する式の直後にカンマをつけます (単一の式だけではタプルを形成しません。これは、式をグループ化するのに丸括弧を使えるようにしなければならないからです)。要素の全くない丸括弧の対を作ると空のタプルになります。
- 変更可能なシーケンス型 (mutable sequence)
変更可能なシーケンスは、作成した後で変更することができます。変更可能なシーケンスでは、添字表記やスライス表記を使って指定された要素に代入を行うことができ、
del
(delete) 文を使って要素を削除することができます。Python に最初から組み込まれている変更可能なシーケンス型は、今のところ二つです:
- リスト型 (list)
リストの要素は任意の Python オブジェクトにできます。リストは、角括弧の中にカンマで区切られた式を並べて作ります。 (長さが 0 や 1 のシーケンスを作るために特殊な場合分けは必要ないことに注意してください。)
- バイト配列
bytearray オブジェクトは変更可能な配列です。組み込みの
bytearray()
コンストラクタによって作成されます。変更可能なことを除けば (つまりハッシュ化できない)、 byte array は変更不能な bytes オブジェクトと同じインターフェースと機能を提供します。
拡張モジュール
array
では、別の変更可能なシーケンス型を提供しています。
- 集合型
集合型は、順序のない、ユニークで不変なオブジェクトの有限集合を表現します。そのため、(配列の)添字を使ったインデックスアクセスはできません。ただし、イテレートは可能で、組み込み関数
len()
は集合の要素数を返します。集合型の一般的な使い方は、集合に属しているかの高速なテスト、シーケンスからの重複の排除、共通集合・和集合・差・対称差といった数学的な演算の計算です。集合の要素には、辞書のキーと同じ普遍性に関するルールが適用されます。数値型は通常の数値比較のルールに従うことに注意してください。もし2つの数値の比較結果が同値である(例えば、
1
と1.0
)なら、そのうちの1つのみを集合に含めることができます。現在、2つの組み込み集合型があります:
- 集合型
可変な集合型です。組み込みの
set()
コンストラクタで作成され、後からadd()
などのいくつかのメソッドで更新できます。- Frozen set 型
不変な集合型です。組み込みの
frozenset()
コンストラクタによって作成されます。 frozenset は不変でハッシュ可能(hashable)なので、別の集合型の要素になったり、辞書のキーにすることができます。
- マップ型 (mapping)
任意のインデクス集合でインデクス化された、有限のオブジェクトからなる集合を表現します。添字表記
a[k]
は、k
でインデクス指定された要素をa
から選択します; 選択された要素は式の中で使うことができ、代入やdel
文の対象にすることができます。組み込み関数len()
は、マップ内の要素数を返します。Python に最初から組み込まれているマップ型は、今のところ一つだけです:
- 辞書型 (dictionary)
ほとんどどんな値でもインデクスとして使えるような、有限個のオブジェクトからなる集合を表します。キー値 (key) として使えない値は、リストや辞書を含む値や、アイデンティティではなく値でオブジェクトが比較される、その他の変更可能な型です。これは、辞書型を効率的に実装する上で、キーのハッシュ値が一定であることが必要だからです。数値型をキーに使う場合、キー値は通常の数値比較における規則に従います: 二つの値が等しくなる場合 (例えば
1
と1.0
)、互いに同じ辞書のエントリを表すインデクスとして使うことができます。辞書は変更可能な型です; 辞書は
{...}
表記で生成します (辞書表現 を参照してください)。
- 呼び出し可能型 (callable type)
関数呼び出し操作 (呼び出し (call) 参照) を行うことができる型です:
- ユーザ定義関数 (user-defined function)
ユーザ定義関数オブジェクトは、関数定義を行うことで生成されます (関数定義 参照)。関数は、仮引数 (formal parameter) リストと同じ数の要素が入った引数リストとともに呼び出されます。
特殊属性:
属性
意味
__doc__
func_doc
関数のドキュメンテーション文字列です。ドキュメンテーションがない場合は
None
になります。書き込み可能
__name__
func_name
関数の名前です
書き込み可能
__module__
関数が定義されているモジュールの名前です。モジュール名がない場合は
None
になります。書き込み可能
__defaults__
func_defaults
デフォルト値を持つ引数に対するデフォルト値が収められたタプルで、デフォルト値を持つ引数がない場合には
None
になります書き込み可能
__code__
func_code
コンパイルされた関数本体を表現するコードオブジェクトです。
書き込み可能
__globals__
func_globals
関数のグローバル変数の入った辞書 (への参照) です --- この辞書は、関数が定義されているモジュールのグローバルな名前空間を決定します。
読み込み専用
__dict__
func_dict
任意の関数属性をサポートするための名前空間が収められています。
書き込み可能
__closure__
func_closure
None
または関数の個々の自由変数 (引数以外の変数) に対して値を結び付けているセル (cell) 群からなるタプルになります。読み込み専用
「書き込み可能」とラベルされている属性のほとんどは、代入された値の型をチェックします。
バージョン 2.4 で変更:
func_name
は書き込み可能になりました.バージョン 2.6 で変更: Python 3 との前方互換のために、ダブルアンダースコアの属性
__closure__
,__code__
,__defaults__
,__globals__
が対応するfunc_*
への別名として導入されました。関数オブジェクトはまた、任意の属性を設定したり取得したりできます。この機能は、例えば関数にメタデータを付与したい場合などに使えます。関数の get や set には、通常のドット表記を使います。 現在の実装では、ユーザ定義の関数でのみ属性をサポートしているので注意して下さい。組み込み関数の属性は将来サポートする予定です。
関数定義に関するその他の情報は、関数のコードオブジェクトから得られます; 後述の内部型 (internal type) に関する説明を参照してください。
- ユーザ定義メソッド (user-defined method)
ユーザ定義のメソッドオブジェクトは、クラスやクラスインスタンス (あるいは
None
) を任意の呼び出し可能オブジェクト (通常はユーザ定義関数) と結合し (combine) ます。読み出し専用の特殊属性:
im_self
はクラスインスタンスオブジェクトで、im_func
は関数オブジェクトです;im_class
は結合メソッド (bound method) においてim_self
が属しているクラスか、あるいは非結合メソッド (unbound method) において、要求されたメソッドを定義しているクラスです;__doc__
はメソッドのドキュメンテーション文字列 (im_func.__doc__
と同じ) です;__name__
はメソッドの名前 (im_func.__name__
と同じ) です;__module__
はメソッドが定義されているモジュールの名前になるか、モジュール名がない場合はNone
になります。バージョン 2.2 で変更: メソッドを定義しているクラスを参照するために
im_self
が使われていました.バージョン 2.6 で変更: Python 3 との前方互換性のために、
im_func
の代わりに__func__
も、im_self
の代わりに__self__
も使うことができます。メソッドもまた、根底にある関数オブジェクトの任意の関数属性に (値の設定はできませんが) アクセスできます。
クラスの属性を (おそらくクラスのインスタンスを介して) 取得する際には、その属性がユーザ定義の関数オブジェクト、非結合 (unbound) のユーザ定義メソッドオブジェクト、あるいはクラスメソッドオブジェクトであれば、ユーザ定義メソッドオブジェクトが生成されることがあります。属性がユーザ定義メソッドオブジェクトの場合、属性を取得する対象のオブジェクトが属するクラスがもとのメソッドオブジェクトが定義されているクラスと同じクラスであるか、またはそのサブクラスであれば、新たなメソッドオブジェクトだけが生成されます。それ以外の場合には、もとのメソッドオブジェクトがそのまま使われます。
クラスからユーザ定義関数オブジェクトを取得する方法でユーザ定義メソッドオブジェクトを生成すると、
im_self
属性はNone
になり、メソッドオブジェクトは非結合 (unbound) であるといいます。クラスのインスタンスからユーザ定義関数オブジェクトを取得する方法でユーザ定義メソッドオブジェクトを生成すると、im_self
属性はインスタンスになり、メソッドオブジェクトは結合 (bound) であるといいます。どちらの場合も、新たなメソッドのim_class
属性は、メソッドの取得が行われたクラスになり、im_func
属性はもとの関数オブジェクトになります。クラスやインスタンスから他のユーザ定義メソッドオブジェクトを取得する方法でユーザ定義メソッドオブジェクトを生成した場合、その動作は関数オブジェクトの場合と同様ですが、新たなインスタンスの
im_func
属性はもとのメソッドオブジェクトの属性ではなく、新たなインスタンスの属性になります。クラスやインスタンスからクラスメソッドオブジェクトを取得する方法でユーザ定義メソッドオブジェクトを生成した場合、
im_self
属性はクラス自体となり、im_func
属性はクラスメソッドの根底にある関数オブジェクトになります。非結合ユーザ定義メソッドオブジェクトの呼び出しの際には、根底にある関数 (
im_func
) が呼び出されます。このとき、最初の引数は適切なクラス (im_class
) またはサブクラスのインスタンスでなければならないという制限が課されています。結合ユーザ定義メソッドオブジェクトの呼び出しの際には、根底にある関数 (
im_func
) が呼び出されます。このとき、クラスインスタンス (im_self
) が引数の先頭に挿入されます。例えば、関数f()
の定義が入ったクラスをC
とし、x
をC
のインスタンスとすると、x.f(1)
の呼び出しはC.f(x, 1)
と同じになります。ユーザ定義メソッドオブジェクトがクラスオブジェクトから派生した際、
im_self
に記憶されている "クラスインスタンス" はクラス自体になります。これは、x.f(1)
やC.f(1)
の呼び出しが根底にある関数をf
としたときの呼び出しf(C,1)
と等価になるようにするためです。関数オブジェクトから (結合または非結合の) メソッドオブジェクトへの変換は、クラスやインスタンスから属性を取り出すたびに行われるので注意してください。場合によっては、属性をローカルな変数に代入しておき、その変数を使って関数呼び出しを行うと効果的な最適化になります。また、上記の変換はユーザ定義関数に対してのみ起こるので注意してください; その他の呼び出し可能オブジェクト (および呼び出し可能でない全てのオブジェクト) は、変換を受けずに取り出されます。それから、クラスインスタンスの属性になっているユーザ定義関数は、結合メソッドに変換できないと知っておくことも重要です; 結合メソッドへの変換が行われるのは、関数がクラスの一属性である場合 だけ です。
- ジェネレータ関数 (generator function)
yield
文 (yield 文 の節を参照) を使う関数もしくはメソッドは ジェネレータ関数 と呼ばれます。そのような関数が呼び出されたときは常に、関数の本体を実行するのに使えるイテレータオブジェクトを返します: イテレータのnext()
メソッドを呼び出すと、yield
文を使って値が提供されるまで関数を実行します。関数のreturn
文を実行するか終端に達したときは、StopIteration
例外が送出され、イテレータが返すべき値の最後まで到達しています。- 組み込み関数 (built-in function)
組み込み関数オブジェクトはC関数へのラッパーです。 組み込み関数の例は
len()
やmath.sin()
(math
は標準の組み込みモジュール) です。 引数の数や型は C 関数で決定されています。 読み出し専用の特殊属性:__doc__
は関数のドキュメンテーション文字列です。 ドキュメンテーションがない場合はNone
になります;__name__
は関数の名前です;__self__
はNone
に設定されています (組み込みメソッドの節も参照してください);__module__
は、関数が定義されているモジュールの名前です。 モジュール名がない場合はNone
になります。- 組み込みメソッド (built-in method)
実際には組み込み関数を別の形で隠蔽したもので、こちらの場合には C 関数に渡される何らかのオブジェクトを非明示的な外部引数として持っています。組み込みメソッドの例は、 alist をリストオブジェクトとしたときの
alist.append()
です。この場合には、読み出し専用の属性__self__
は alist で表されるオブジェクトになります。- クラス型 (class type)
クラス型、あるいは "新しいクラス型 (new-style class)" や呼び出し可能オブジェクトです。クラス型オブジェクトは通常、そのクラスの新たなインスタンスを生成する際のファクトリクラスとして振舞いますが、
__new__()
をオーバライドして、バリエーションを持たせることもできます。呼び出しの際に使われた引数は__new__()
に渡され、さらに典型的な場合では新たなインスタンスを初期化するために__init__()
に渡されます。- 旧クラス型 (classic class)
(旧) クラスオブジェクトは後で詳しく説明します。クラスオブジェクトが呼び出されると、新たにクラスインスタンス (後述) が生成され、返されます。この操作には、クラスの
__init__()
メソッドの呼び出し (定義されている場合) が含まれています。呼び出しの際に使われた引数は、すべて__init__()
メソッドに渡されます。__init__()
メソッドがない場合、クラスは引数なしで呼び出さなければなりません。- クラスインスタンス (class instance)
クラスインスタンスは後で詳しく説明します。クラスインスタンスはクラスが
__call__()
メソッドを持っている場合にのみ呼び出すことができます;x(arguments)
とすると、x.__call__(arguments)
呼び出しを短く書けます。
- モジュール (module)
モジュールは
import
文で import します (import 文 参照)。モジュールオブジェクトは、辞書オブジェクト (モジュール内で定義されている関数が func_globals 属性で参照している辞書です) で実装された名前空間を持っています。属性への参照は、この辞書に対する検索 (lookup) に翻訳されます。例えば、m.x
はm.__dict__["x"]
と同じです。モジュールオブジェクトには、モジュールを初期化するために使われるコードオブジェクトは入っていません (一度初期化が終わればもう必要ないからです)。属性の代入を行うと、モジュールの名前空間辞書の内容を更新します。例えば、
m.x = 1
はm.__dict__["x"] = 1
と同じです。読み出し専用の特殊属性:
__dict__
はモジュールの名前空間で、辞書オブジェクトです。CPython がモジュール辞書を削除する方法により、モジュール辞書が生きた参照を持っていたとしてもその辞書はモジュールがスコープから外れた時に削除されます。これを避けるには、辞書をコピーするか、辞書を直接使っている間モジュールを保持してください。
定義済みの (書き込み可能な) 属性:
__name__
はモジュールの名前です;__doc__
は関数のドキュメンテーション文字列です。ドキュメンテーションがない場合はNone
になります; モジュールがファイルからロードされた場合、__file__
はロードされたモジュールファイルのパス名です。インタプリタに静的にリンクされている C モジュールの場合、__file__
属性はありません; 共有ライブラリから動的にロードされた拡張モジュールの場合、この属性は共有ライブラリファイルのパス名になります。- クラス
2 種類のクラス、 type (新スタイルクラス) と class object (旧スタイルクラス) の両方とも、通常はクラス定義 (クラス定義 参照) で生成されます。クラスは辞書で実装された名前空間を持っています。クラス属性への参照は、この辞書に対する検索 (lookup) に翻訳されます。例えば、
C.x
はC.__dict__["x"]
と同じです。(ただし、特に新スタイルクラスにおいて、属性参照の意味を変えられる幾つかのフックがあります)。属性がこの検索で見つからない場合、現在のクラスの基底クラスへと検索を続けます。旧スタイルクラスの場合、検索は深さ優先 (depth-first)、かつ基底クラスの挙げられているリスト中の左から右 (left-to-right) の順番で行われます。新スタイルクラスは、より複雑な、C3メソッド解決順序(MRO=method resolution order) を利用していて、複数の継承パスが共通の祖先にたどり着く「ダイアモンド継承」があっても正しく動作します。 C3 MRO についてのより詳細な情報は、2.3リリースに付属するドキュメントにあります。 (https://www.python.org/download/releases/2.3/mro/)クラス (
C
とします) への属性参照で、要求している属性がユーザ定義関数オブジェクトや、C
やその基底クラスに関連付けられている非結合のユーザ定義メソッドオブジェクトである場合、im_class
属性がC
であるような非結合ユーザ定義メソッドオブジェクトに変換されます。要求している属性がクラスメソッドオブジェクトの場合、そのim_self
属性がC
であるようなユーザ定義メソッドオブジェクトに変換されます。要求している属性が静的メソッドオブジェクトの場合、静的メソッドオブジェクトでラップされたオブジェクトに変換されます。クラスから取り出した属性と実際に__dict__
に入っているものが異なるような他の場合については、 デスクリプタ (descriptor) の実装 を参照してください (新スタイルクラスだけがディスクリプタをサポートしていることに注意してください)。クラス属性を代入すると、そのクラスの辞書だけが更新され、基底クラスの辞書は更新しません。
クラスオブジェクトを呼び出す (上記を参照) と、クラスインスタンスを生成します (下記を参照)。
特殊属性:
__name__
はクラス名です;__module__
はクラスが定義されたモジュール名です;__dict__
はクラスが持つ名前空間が入った辞書です;__bases__
は基底クラスからなるタプル (空もしくは要素が 1 つしかないこともあります) で、基底クラスのリストに表れる順序で並んでいます;__doc__
はクラスのドキュメント文字列で、未定義の場合は None です。- クラスインスタンス (class instance)
クラスインスタンスはクラスオブジェクト (上記参照) を呼び出して生成します。クラスインスタンスは辞書で実装された名前空間を持っており、属性参照の時にはこの辞書が最初に検索されます。辞書内に属性が見つからず、かつインスタンスのクラスに該当する属性名がある場合、検索はクラス属性にまで広げられます。見つかったクラス属性がユーザ定義関数オブジェクトや、インスタンスのクラス (
C
とします) やその基底クラスに関連付けられている非結合のユーザ定義メソッドオブジェクトの場合、im_class
属性がC
でim_self
属性がインスタンスになっている結合ユーザ定義メソッドオブジェクトに変換されます。静的メソッドやクラスメソッドオブジェクトもまた、C
から取り出した場合と同様に変換されます; 上記の "クラス" を参照してください。クラスから取り出した属性と実際に__dict__
に入っているものが異なるような他の場合については、 デスクリプタ (descriptor) の実装 節を参照してください。クラス属性が見つからず、かつオブジェクトのクラスが__getattr__()
メソッドを持っている場合、このメソッドを呼び出して属性名の検索を充足させます。属性の代入や削除を行うと、インスタンスの辞書を更新しますが、クラスの辞書を更新することはありません。クラスで
__setattr__()
や__delattr__()
メソッドが定義されている場合、直接インスタンスの辞書を更新する代わりにこれらのメソッドが呼び出されます。クラスインスタンスは、ある特定の名前のメソッドを持っている場合、数値型やシーケンス型、あるいはマップ型のように振舞うことができます。 特殊メソッド名 を参照してください。
- ファイル (file)
ファイルオブジェクトは開かれたファイルを表します。ファイルオブジェクトは組み込み関数
open()
や、os.popen()
,os.fdopen()
, および socke オブジェクトのmakefile()
メソッド (その他の拡張モジュールで提供されている関数やメソッド) で生成されます。sys.stdin
,sys.stdout
およびsys.stderr
といったオブジェクトは、インタプリタの標準入力、標準出力、および標準エラー出力ストリームに対応するよう初期化されます。ファイルオブジェクトに関する完全な記述については、 ファイルオブジェクト を参照してください。- 内部型 (internal type)
インタプリタが内部的に使っているいくつかの型は、ユーザに公開されています。これらの定義は将来のインタプリタのバージョンでは変更される可能性がありますが、ここでは記述の完全性のために触れておきます。
- コードオブジェクト
コードオブジェクトは バイトコンパイルされた (byte-compiled) 実行可能な Python コード、別名バイトコード(bytecode) を表現します。コードオブジェクトと関数オブジェクトの違いは、関数オブジェクトが関数のグローバル変数 (関数を定義しているモジュールのグローバル) に対して明示的な参照を持っているのに対し、コードオブジェクトにはコンテキストがないということです; また、関数オブジェクトではデフォルト引数値を記憶できますが、コードオブジェクトではできません (実行時に計算される値を表現するため)。関数オブジェクトと違い、コードオブジェクトは変更不可能で、変更可能なオブジェクトへの参照を (直接、間接に関わらず) 含みません。
読み出し専用の特殊属性:
co_name
は関数名を表します;co_argcount
は固定引数 (positional argument) の数です;co_nlocals
は関数が使う (引数を含めた) ローカル変数の数です;co_varnames
はローカル変数名の入ったタプルです (引数名から始まっています);co_cellvars
はネストされた関数で参照されているローカル変数の名前が入ったタプルです;co_freevars
は自由変数の名前が入ったタプルです。co_code
はバイトコード列を表現している文字列です;co_consts
はバイトコードで使われているリテラルの入ったタプルです;co_names
はバイトコードで使われている名前の入ったタプルです;co_filename
はバイトコードのコンパイルが行われたファイル名です;co_firstlineno
は関数の最初の行番号です;co_lnotab
はバイトコードオフセットから行番号への対応付けをコード化した文字列です (詳細についてはインタプリタのソースコードを参照してください);co_stacksize
は関数で (ローカル変数の分も含めて) 必要なスタックサイズです;co_flags
はインタプリタ用の様々なフラグをコード化した整数です。以下のフラグビットが
co_flags
で定義されています:0x04
ビットは、関数が*arguments
構文を使って任意の数の固定引数を受理できる場合に立てられます;0x08
ビットは、関数が**keywords
構文を使ってキーワード引数を受理できる場合に立てられます;0x20
ビットは、関数がジェネレータである場合に立てられます。将来機能 (future feature) 宣言 (
from __future__ import division
) もまた、co_flags
のビットを立てることで、コードオブジェクトが特定の機能を有効にしてコンパイルされていることを示します:0x2000
ビットは、関数が将来機能を有効にしてコンパイルされている場合に立てられます; 以前のバージョンの Python では、0x10
および0x1000
ビットが使われていました。co_flags
のその他のビットは将来に内部的に利用するために予約されています。コードオブジェクトが関数を表現している場合、
co_consts
の最初の要素は関数のドキュメンテーション文字列になります。ドキュメンテーション文字列が定義されていない場合にはNone
になります。
- フレーム (frame) オブジェクト
フレームオブジェクトは実行フレーム (execution frame) を表します。実行フレームはトレースバックオブジェクト内に出現します (下記参照)。
読み出し専用の特殊属性:
f_back
は (呼び出し側にとっての) 以前のスタックフレームです。呼び出し側がスタックフレームの最下段である場合にはNone
です;f_code
は現在のフレームで実行しようとしているコードオブジェクトです;f_locals
はローカル変数を検索するために使われる辞書です;f_globals
はグローバル変数用です;f_builtins
は組み込みの (Python 固有の) 名前です;f_restricted
は、関数が制限つき実行 (restricted execution) モードで実行されているかどうかを示すフラグです;f_lasti
は厳密な命令コード (コードオブジェクト中のバイトコード文字列へのインデクス) です。書き込み可能な特殊属性:
f_trace
がNone
でない場合、各ソースコード行の先頭で呼び出される関数になります;f_exc_type
,f_exc_value
,f_exc_traceback
は、現在のフレームが以前に引き起こした例外が提供する親フレーム内でもっとも最近捕捉された例外を表します (それ以外の場合は、これらはNone
になります);f_lineno
はフレーム中における現在の行番号です --- トレース関数 (trace function) 側でこの値に書き込みを行うと、指定した行にジャンプします (最下段の実行フレームにいるときのみ) 。デバッガでは、 f_fileno を書き込むことで、ジャンプ命令 (Set Next Statement 命令とも呼ばれます) を実装できます。- トレースバック (traceback) オブジェクト
トレースバックオブジェクトは例外のスタックトレースを表現します。トレースバックオブジェクトは例外が発生した際に生成されます。例外ハンドラを検索して実行スタックを戻っていく際、戻ったレベル毎に、トレースバックオブジェクトが現在のトレースバックの前に挿入されます。例外ハンドラに入ると、スタックトレースをプログラム側で利用できるようになります (try 文 を参照)。トレースバックは
sys.exc_traceback
として得ることができ、sys.exc_info()
が返すタプルの三番目の要素としても得られます. インタフェースとしては後者の方が推奨されていますが、これはプログラムがマルチスレッドを使っている場合に正しく動作するからです。プログラムに適切なハンドラがない場合、スタックトレースは (うまく書式化されて) 標準エラーストリームに書き出されます; インタプリタが対話的に実行されている場合、sys.last_traceback
として得ることもできます。読み出し専用の特殊属性:
tb_next
はスタックトレース内の (例外の発生しているフレームに向かって) 次のレベルです。次のレベルが存在しない場合にはNone
になります;tb_frame
は現在のレベルにおける実行フレームを指します;tb_lineno
は例外の発生した行番号です;tb_lasti
は厳密な命令コードです。トレースバック内の行番号や最後に実行された命令は、try
文内で例外が発生し、かつ対応するexcept
節やfinally
節がない場合には、フレームオブジェクト内の行番号とは異なるかもしれません。- スライス (slice) オブジェクト
スライスオブジェクトは 拡張スライス構文 (extended slice syntax) が使われた際にスライスを表現するために使われます。拡張スライス構文とは、二つのコロンや、コンマで区切られた複数のスライスや省略符号 (ellipse) を使ったスライスで、例えば
a[i:j:step]
、a[i:j, k:l]
、あるいはa[..., i:j]
です。スライスオブジェクトは組み込み関数slice()
で生成されます。読み込み専用の特殊属性:
start
は下限です;stop
は上限です;step
はステップの値です; それぞれ省略された場合はNone
となっています。これらの属性は任意の型を持てます。スライスオブジェクトはメソッドを一つサポートします:
-
slice.
indices
(self, length)¶ このメソッドは単一の整数引数 length を取り、 length 個の要素からなるシーケンスに適用した際にスライスオブジェクトから提供することになる、拡張スライスに関する情報を計算します。このメソッドは三つの整数からなるタプルを返します; それぞれ start および stop のインデクスと、 step またはスライス間の幅に対応します。インデクス値がないか、範囲外の値である場合、通常のスライスに対して一貫性のあるやりかたで扱われます。
バージョン 2.3 で追加.
-
- 静的メソッド (static method) オブジェクト
静的メソッドは、上で説明したような関数オブジェクトからメソッドオブジェクトへの変換を阻止するための方法を提供します。静的メソッドオブジェクトは他の何らかのオブジェクト、通常はユーザ定義メソッドオブジェクトを包むラッパです。静的メソッドをクラスやクラスインスタンスから取得すると、実際に返されるオブジェクトはラップされたオブジェクトになり、それ以上は変換の対象にはなりません。静的メソッドオブジェクトは通常呼び出し可能なオブジェクトをラップしますが、静的オブジェクト自体は呼び出すことができません。静的オブジェクトは組み込みコンストラクタ
staticmethod()
で生成されます。- クラスメソッドオブジェクト
クラスメソッドオブジェクトは、静的メソッドオブジェクトに似て、別のオブジェクトを包むラッパであり、そのオブジェクトをクラスやクラスインスタンスから取り出す方法を代替します。このようにして取得したクラスメソッドオブジェクトの動作については、上の "ユーザ定義メソッド (user-defined method)" で説明されています。クラスメソッドオブジェクトは組み込みのコンストラクタ
classmethod()
で生成されます。
3.3. 新スタイルと旧スタイル¶
クラスとインスタンスは好みに合わせて2種類の方法で記述することができます: 旧スタイル(もしくはクラシックスタイル)と新スタイルです。
Python 2.1 までは、 class
の概念は type
の概念とは無関係で、また、旧スタイルクラスが唯一のものでした。旧スタイルクラスでは、 x.__class__
は x のクラスを提供はしますが、 type(x)
は常に <type 'instance'>
になります。これは、すべての旧スタイルのインスタンスが、それらのクラスとは独立の、 instance
と呼ばれる一つの内蔵型として実行されるということを反映しています。
新スタイルのクラスは、 class
と type
の概念を統一するために Python 2.2 で導入されました。新スタイルのクラスはユーザ定義型そのもので、それ以上でも以下でもありません。もし、 x が新スタイルクラスのインスタンスであった場合、 type(x)
は x.__class__
と同じになります。 (ただし、これは保証されている動作ではありません -- 新スタイルクラスのインスタンスは、 x.__class__
で返る値をオーバーライドすることができます。)
新スタイルクラスを導入する一番の理由は、メタモデルを用いた統一的なオブジェクトモデルを提供することにあります。また、ほとんどの組み込み型のサブクラスが作成できる、属性を計算するための"デスクリプタ"の導入できる等の利点があります。
互換性のために、デフォルトではクラスは旧スタイルになります。新スタイルのクラスは、他の新スタイルクラス (すなわち型)を親クラスとして定義する、もしくは、他の親クラスが必要ない場合に "最上位型" object
を継承することで作成することができます。新スタイルクラスの動作は旧スタイルクラスの動作とは、 type()
が何を返すかといったことをはじめ、何点か重要な部分が異なります。特殊メソッドの呼び出しなど、これらの変更は新オブジェクトモデルの基盤となっています。それ以外の部分は、多重継承時のメソッドの解決順などのように、互換性の問題で以前は実装が不可能であった"修正"が新クラスに含まれています。
このマニュアルは Python のクラスメカニズムに関する総合的な情報を提供しようとしていますが、新スタイルクラスについては、まだ足りない部分があるかもしれません。より詳細な情報を得たい場合は、 https://www.python.org/doc/newstyle/ を参照してください。
Python 3 では旧スタイルクラスが削除されて、新スタイルクラスが唯一のクラスになりました。
3.4. 特殊メソッド名¶
特殊な名前をもったメソッドを定義することで、特殊な構文 (算術演算や添え字表記、スライス表記のような) 特定の演算をクラスで実装することができます。これは、個々のクラスが Python 言語で提供されている演算子に対応した独自の振る舞いをできるようにするための、演算子のオーバロード (operator overloading) に対する Python のアプローチです。例えば、あるクラスが __getitem__()
という名前のメソッドを定義しており、 x
がこのクラスのインスタンスであるとすると、 x[i]
は旧スタイルクラスの場合 x.__getitem__(i)
と、新スタイルクラスの場合 type(x).__getitem__(x, i)
とほぼ等価になります。特に注釈のない限り、適切なメソッドが定義されていない場合にこのような演算を行おうとすると例外が送出されます。 (発生する例外はたいてい、 AttributeError
か TypeError
です。)
組み込み型を模倣するクラスを実装するときは、真似されるオブジェクトにとって意味がある範囲に実装をとどめるのが重要です。例えば、あるシーケンスは個々の要素の取得はきちんと動くかもしれませんが、スライスの展開が意味を為さないかもしれません。 (W3C のドキュメントオブジェクトモデルにある NodeList
インターフェースがその一例です。)
3.4.1. 基本的なカスタマイズ¶
-
object.
__new__
(cls[, ...])¶ クラス cls の新しいインスタンスを作るために呼び出されます。
__new__()
は静的メソッドで (このメソッドは特別扱いされているので、明示的に静的メソッドと宣言する必要はありません)、インスタンスを生成するよう要求されているクラスを第一引数にとります。残りの引数はオブジェクトのコンストラクタの式 (クラスの呼び出し文) に渡されます。__new__()
の戻り値は新しいオブジェクトのインスタンス (通常は cls のインスタンス) でなければなりません。典型的な実装では、クラスの新たなインスタンスを生成するときには
super(currentclass, cls).__new__(cls[, ...])
に適切な引数を指定してスーパクラスの__new__()
メソッドを呼び出し、新たに生成されたインスタンスに必要な変更を加えてから返します。__new__()
が cls のインスタンスを返した場合、__init__(self[, ...])
のようにしてインスタンスの__init__()
が呼び出されます。このとき、 self は新たに生成されたインスタンスで、残りの引数は__new__()
に渡された引数と同じになります。__new__()
が cls のインスタンスを返さない場合、インスタンスの__init__()
メソッドは呼び出されません。__new__()
の主な目的は、変更不能な型 (int, str, tuple など) のサブクラスでインスタンス生成をカスタマイズすることにあります。また、クラス生成をカスタマイズするために、カスタムのメタクラスでよくオーバーライドされます。
-
object.
__init__
(self[, ...])¶ インスタンスが (
__new__()
によって) 生成された後、それが呼び出し元に返される前に呼び出されます。引数はクラスのコンストラクタ式に渡したものです。基底クラスとその派生クラスがともに__init__()
メソッドを持つ場合、派生クラスの__init__()
メソッドは基底クラスの__init__()
メソッドを明示的に呼び出して、インスタンスの基底クラス部分が適切に初期化されること保証しなければなりません。例えば、BaseClass.__init__(self, [args...])
。__new__()
と__init__()
は共同してオブジェクトを構成する (__new__()
が作成し、__init__()
がそれをカスタマイズする) ので、__init__()
が非None
値を返すことがあってはなりません; さもなければ、実行時にTypeError
が送出される原因になります。
-
object.
__del__
(self)¶ インスタンスが消滅させられる際に呼び出されます。このメソッドはデストラクタ (destructor) とも呼ばれます。基底クラスとその派生クラスがともに
__del__()
メソッドを持つ場合、派生クラスの__del__()
メソッドは基底クラスの__del__()
メソッドを明示的に呼び出して、インスタンスの基底クラス部分が適切に消滅処理されること保証しなければなりません。__del__()
メソッドでインスタンスに対する新たな参照を作ることで、インスタンスの消滅を遅らせることができます (とはいえ、推奨しません!)。このようにすると、新たに作成された参照がその後削除された際にもう一度__del__()
メソッドが呼び出されます。インタプリタが終了する際に残っているオブジェクトに対して、__del__()
メソッドが呼び出される保証はありません。注釈
del x
は直接x.__del__()
を呼び出しません --- 前者はx
への参照カウント (reference count) を 1 つ減らし、後者はx
への参照カウントがゼロになった際にのみ呼び出されます。オブジェクトへの参照カウントがゼロになるのを妨げる可能性のあるよくある状況には、以下のようなものがあります: 複数のオブジェクト間における循環参照 (二重リンクリストや、親と子へのポインタを持つツリーデータ構造); 例外を捕捉した関数におけるスタックフレーム上にあるオブジェクトへの参照 (sys.exc_traceback
に記憶されているトレースバックが、スタックフレームを生き延びさせます); または、対話モードでハンドルされなかった例外を送出したスタックフレーム上にあるオブジェクトへの参照 (sys.last_traceback
に記憶されているトレースバックが、スタックフレームを生き延びさせます); 最初の状況については、明示的に循環参照を壊すしか解決策はありません; 後者の二つの状況は、None
をsys.exc_traceback
やsys.last_traceback
に入れることで解決できます。ごみオブジェクトと化した循環参照は、オプションの循環参照検出機構 (cycle detector) が有効にされている場合 (これはデフォルトの設定です) には検出されますが、検出された循環参照を消去するのは Python レベルで__del__()
メソッドが定義されていない場合だけです。__del__()
メソッドが循環参照検出機構でどのように扱われるか、とりわけgarbage
値の記述に関しては、gc
モジュールのドキュメントを参照してください。警告
__del__()
メソッドの呼び出しが起きるのは不安定な状況下なので、__del__()
の実行中に発生した例外は無視され、代わりにsys.stderr
に警告が出力されます。また、 (例えばプログラムの実行終了による) モジュールの削除に伴って__del__()
が呼び出される際には、__del__()
メソッドが参照している他のグローバル変数はすでに削除されていたり、削除中(例えば、import機構のシャットダウン中)かもしれません。この理由から、__del__()
メソッドでは外部の不変関係を維持する上で絶対最低限必要なことだけをすべきです。バージョン 1.5 からは、単一のアンダースコアで始まるようなグローバル変数は、他のグローバル変数が削除される前にモジュールから削除されるように Python 側で保証しています; これらのアンダースコア付きグローバル変数は、__del__()
が呼び出された際に、import されたモジュールがまだ残っているか確認する上で役に立ちます。-R
コマンドラインオプションも参照して下さい。
-
object.
__repr__
(self)¶ 組み込み関数
repr()
や、文字列への変換 (逆クオート表記: reverse quote) の際に呼び出され、オブジェクトを表す "公式の (official)" 文字列を計算します。可能な場合には、この値は同じ値を持ったオブジェクトを (適切な環境で) 再生成するために使えるような有効な Python 式に似せるべきです。それが不可能なら、<...some useful description...>
形式の文字列を返してください。戻り値は文字列オブジェクトでなければなりません。クラスが__repr__()
を定義しているが__str__()
を定義していない場合、そのクラスのインスタンスに対する "非公式の (informal)" 文字列表現が必要なときにも__repr__()
が使われます。この関数はデバッグの際によく用いられるので、たくさんの情報を含み、あいまいでないような表記にすることが重要です。
-
object.
__str__
(self)¶ 組み込み関数
str()
およびprint
文によって呼び出され、オブジェクトを表す "非公式の" 文字列を計算します。このメソッドは、有効な Python 式を返さなくても良いという点で、__repr__()
と異なります: その代わり、より便利で分かりやすい表現を返すようにしてください。戻り値は文字列オブジェクトでなければなりません。
-
object.
__lt__
(self, other)¶ -
object.
__le__
(self, other)¶ -
object.
__eq__
(self, other)¶ -
object.
__ne__
(self, other)¶ -
object.
__gt__
(self, other)¶ -
object.
__ge__
(self, other)¶ バージョン 2.1 で追加.
これらのメソッドは "拡張比較 (rich comparison)" メソッドと呼ばれ、下記の
__cmp__()
に優先して呼び出されます。演算子シンボルとメソッド名の対応は以下の通りです:x<y
はx.__lt__(y)
を呼び出します;x<=y
はx.__le__(y)
を呼び出します;x==y
はx.__eq__(y)
を呼び出します;x!=y
およびx<>y
はx.__ne__(y)
を呼び出します;x>y
はx.__gt__(y)
を呼び出します;x>=y
はx.__ge__(y)
を呼び出します。拡張比較メソッドは、与えられた引数のペアに対する操作を実装していないときに、
NotImplemented
というシングルトンを返すかもしれません。慣例として、正常に比較が行われたときにはFalse
かTrue
を返します。しかし、これらのメソッドは任意の値を返すことができるので、比較演算子がブール値のコンテキスト(たとえば、if
文の条件部分)で使われた場合、 Python はその値に対してbool()
を呼び出して結果の真偽を判断します。比較演算子間には、暗黙的な論理関係はありません。すなわち、
x==y
が真である場合、暗黙のうちにx!=y
が偽になるわけではありません。従って、__eq__()
を実装する際、演算子が期待通りに動作するようにするために__ne__()
も定義する必要があります。カスタムの比較演算をサポートしていて、辞書のキーに使うことができるハッシュ可能(hashable) オブジェクトを作るときの重要な注意点について、__hash__()
のドキュメント内に書かれているので参照してください。これらのメソッドには、(左引数が演算をサポートしないが、右引数はサポートする場合に用いられるような) 鏡像となる (引数を入れ替えた) バージョンは存在しません; むしろ、
__lt__()
と__gt__()
は互いに鏡像であり、__le__()
と__ge__()
、および__eq__()
と__ne__()
はそれぞれ互いに鏡像です。拡張比較メソッドの引数には型強制 (coerce) が起こりません。
単一の基本演算から順序付けするための演算を自動的に生成したい場合には、
functools.total_ordering()
を参照してください。
-
object.
__cmp__
(self, other)¶ 拡張比較 (上参照) が定義されていない場合、比較演算によって呼び出されます。
self < other
である場合には負の値、self == other
ならばゼロ、self > other
であれば正の値を返さなければなりません。演算__cmp__()
、__eq__()
および__ne__()
がいずれも定義されていない場合、クラスインスタンスはオブジェクトのアイデンティティ("アドレス") で比較されます。自作の比較演算をサポートするオブジェクトや、辞書のキーとして使えるオブジェクトを生成するには、__hash__()
に関する記述を参照してください。 (注意:__cmp__()
が例外を伝播しないという制限は Python 1.5 から除去されました。)
-
object.
__rcmp__
(self, other)¶ バージョン 2.1 で変更: もはやサポートされていません.
-
object.
__hash__
(self)¶ 組み込みの
hash()
関数や、set
,frozenset
,dict
のようなハッシュを使ったコレクション型の要素に対する操作から呼び出されます。__hash__()
は整数を返さなければなりません。 このメソッドに必要な性質は、比較結果が等しいオブジェクトは同じハッシュ値を持つということです; オブジェクトを比較するときでも利用される要素をタプルに詰めてハッシュ値を計算することで、それぞれの要素のハッシュ値を混合することをおすすめします。def __hash__(self): return hash((self.name, self.nick, self.color))
クラスが
__cmp__()
や__eq__()
メソッドを定義していない場合、__hash__()
メソッドも定義してはなりません; クラスが__cmp__()
または__eq__()
を定義しているが、__hash__()
を定義していない場合、インスタンスを辞書のキーとして使うことはできません。クラスが変更可能なオブジェクトを定義しており、__cmp__()
または__eq__()
メソッドを実装している場合、__hash__()
を定義してはなりません。これは、辞書の実装においてハッシュ値が変更不能であることが要求されているからです (オブジェクトのハッシュ値が変化すると、キーが誤ったハッシュバケツ (hash bucket) に入っていることになってしまいます)。ユーザー定義クラスはデフォルトで
__cmp__()
と__hash__()
メソッドを持っています。これらは、同一以外のすべてのオブジェクトに対して比較結果が偽になり、x.__hash__()
はid(x)
から得られる結果を返します。親クラスから
__hash__()
メソッドを継承して、__cmp__()
か__eq__()
の意味を変更している(例えば、デフォルトの同一性ベースの同値関係から値ベースの同値関係に変更する) クラスのハッシュ値は妥当ではなくなるので、__hash__ = None
をクラス定義に書く事で、明示的にハッシュ不可能であることを宣言できます。こうすると、プログラムがそのクラスのインスタンスのハッシュ値を取得しようとしたときに適切なTypeError
例外を送出するようになるだけでなく、 (TypeError
を発生させる__hash__()
メソッドを持つクラスと違って)isinstance(obj, collections.Hashable)
をチェックしたときに、ハッシュ不可能と判定されるようになります。バージョン 2.5 で変更:
__hash__()
は現在では長整数オブジェクトも返せるようになりました。 32ビット整数はこのオブジェクトのハッシュから導出されます。
-
object.
__nonzero__
(self)¶ 真値テストや組み込み演算
bool()
を実現するために呼び出されます;False
またはTrue
か、等価な整数値0
または1
を返さなければなりません。このメソッドが定義されていない場合、__len__()
が定義されていれば呼び出され、その結果が nonzero であれば真になります。__len__()
と__nonzero__()
のどちらもクラスで定義されていない場合、そのクラスのインスタンスはすべて真の値を持つものとみなされます。
3.4.2. 属性値アクセスをカスタマイズする¶
以下のメソッドを定義して、クラスインスタンスへの属性値アクセス ( 属性値の使用、属性値への代入、 x.name
の削除) の意味をカスタマイズすることができます。
-
object.
__getattr__
(self, name)¶ 属性値の検索を行った結果、通常の場所に属性値が見つからなかった場合 (すなわち、
self
のインスタンス属性でなく、かつクラスツリーにも見つからなかった場合) に呼び出されます。name
は属性名です。このメソッドは (計算された) 属性値を返すか、AttributeError
例外を送出しなければなりません。通常のメカニズムを介して属性値が見つかった場合、
__getattr__()
は呼び出されないので注意してください。(これは、__getattr__()
と__setattr__()
の間に意図的に導入された非対称性です。) これは、効率性のためと、こうしなければ__getattr__()
がインスタンスの他の属性値にアクセスする方法がなくなるためです。少なくともインスタンス変数に対しては、値をインスタンスの属性値辞書に挿入しないようにして (代わりに他のオブジェクトに挿入することで) 属性値が完全に制御されているように見せかけられることに注意してください。新スタイルクラスで実際に完全な制御を行う方法は、以下の__getattribute__()
メソッドを参照してください。
-
object.
__setattr__
(self, name, value)¶ 属性値への代入が試みられた際に呼び出されます。このメソッドは通常の代入メカニズム (すなわち、インスタンス辞書への値の代入) の代わりに呼び出されます。 name は属性名で、 value はその属性に代入する値です。
__setattr__()
の中でインスタンス属性値への代入が必要な場合、単にself.name = value
としてはなりません --- このようにすると、自分自身に対する再帰呼び出しがおきてしまいます。その代わりに、インスタンス属性の辞書に値を挿入してください。例えば、self.__dict__[name] = value
とします。新しい形式のクラスでは、インスタンス辞書にアクセスするのではなく、基底クラスのメソッドを同じ属性名で呼び出します。例えば、object.__setattr__(self, name, value)
とします。
-
object.
__delattr__
(self, name)¶ __setattr__()
に似ていますが、代入ではなく値の削除を行います。このメソッドを実装するのは、オブジェクトにとってdel obj.name
が意味がある場合だけにしなければなりません。
3.4.2.1. 新しい形式のクラスのための別の属性アクセス¶
以下のメソッドは新しい形式のクラス (new-style class) のみに適用されます。
-
object.
__getattribute__
(self, name)¶ クラスのインスタンスに対する属性アクセスを実装するために、無条件に呼び出されます。クラスが
__getattr__()
も定義している場合、__getattr__()
は、__getattribute__()
で明示的に呼び出すか、AttributeError
例外を送出しない限り呼ばれません。このメソッドは (計算された) 属性値を返すか、AttributeError
例外を送出します。このメソッドが再帰的に際限なく呼び出されてしまうのを防ぐため、実装の際には常に、必要な属性全てへのアクセスで、例えばobject.__getattribute__(self, name)
のように基底クラスのメソッドを同じ属性名を使って呼び出さなければなりません。注釈
ビルトイン関数や言語構文により暗黙的に特殊メソッドが検索されるときは、このメソッドの呼び出しはバイパスされるでしょう。 新スタイルクラスの特殊メソッド検索 を参照してください。
3.4.2.2. デスクリプタ (descriptor) の実装¶
以下のメソッドは、このメソッドを持つクラス (いわゆる デスクリプタ(descriptor) クラス) のインスタンスが、 オーナー (owner) クラスに存在するときにのみ適用されます (デスクリプタは、オーナーのクラス辞書か、その親のいずれかのクラス辞書になければなりません)。
以下の例では、"属性" とは、名前がオーナークラスの __dict__
のプロパティ (porperty) のキーであるような属性を指します。
-
object.
__get__
(self, instance, owner)¶ オーナクラスの属性を取得する (クラス属性へのアクセス) 際や、オーナクラスのインスタンスの属性を取得する (インスタンス属性へのアクセス) 場合に呼び出されます。 owner は常にオーナクラスです。一方、 instance は属性へのアクセスを仲介するインスタンスか属性が owner を介してアクセスされる場合は
None
になります。このメソッドは (計算された) 属性値を返すか、AttributeError
例外を送出しなければなりません。
-
object.
__set__
(self, instance, value)¶ オーナクラスのインスタンス instance 上の属性を新たな値 value に設定する際に呼び出されます。
-
object.
__delete__
(self, instance)¶ オーナクラスのインスタンス instance 上の属性を削除する際に呼び出されます。
3.4.2.3. デスクリプタの呼び出し¶
一般にデスクリプタとは、特殊な "束縛に関する動作 (binding behaviour)" をもつオブジェクト属性のことです。デスクリプタは、デスクリプタプロトコル (descriptor protocol) のメソッド: __get__()
, __set__()
, および __delete__()
を使って、属性アクセスをオーバライドしているものです。これらのメソッドのいずれかがオブジェクトに対して定義されている場合、オブジェクトはデスクリプタであるといいます。
属性アクセスのデフォルトの動作は、オブジェクトの辞書から値を取り出したり、値を設定したり、削除したりするというものです。例えば、 a.x
による属性の検索では、まず a.__dict__['x']
、次に type(a).__dict__['x']
、そして type(a)
の基底クラスでメタクラスでないものに続く、といった具合に連鎖が起こります。
しかしながら、検索対象となる値が、デスクリプタメソッドのいずれかを定義しているオブジェクトの属性値である場合、Python はデフォルトの動作をオーバライドして、デスクリプタメソッドの方を呼び出します。前後する呼び出し連鎖の中のどこでデスクリプタメソッドが呼び出されるかは、どのデスクリプタメソッドが定義されているかと、どうやってデスクリプタメソッドが呼ばれるかに依存します。デスクリプタは新しい形式のオブジェクトやクラス (object()
や type()
をサブクラス化したもの) だけに対して呼び出されるので注意してください。
デスクリプタ呼び出しの基点となるのは、属性名への束縛 (binding) 、すなわち a.x
です。引数がどのようにデスクリプタに結合されるかは a
に依存します:
- 直接呼び出し (Direct Call)
最も単純で、かつめったに使われない呼び出し操作は、コード中で直接デスクリプタメソッドの呼び出し:
x.__get__(a)
を行うというものです。- インスタンス束縛 (Instance Binding)
新しい形式のクラスのインスタンスに対する束縛では、
a.x
は呼び出し:type(a).__dict__['x'].__get__(a, type(a))
に変換されます。- クラス束縛 (Class Binding)
新しい形式のクラスに対する束縛では、
A.x
は呼び出し:A.__dict__['x'].__get__(None, A)
に変換されます。- super 束縛 (Super Binding)
a
がsuper
のインスタンスである場合、束縛super(B, obj).m()
を行うとまずA
、続いてB
に対してobj.__class_.__mro__
を検索し、次に呼び出し:A.__dict__['m'].__get__(obj, obj.__class__)
でデスクリプタを呼び出します。
インスタンス束縛では、デスクリプタ呼び出しの優先順位はどのデスクリプタが定義されているかに依存します。データデスクリプタは、 __get__()
と __set__()
、 __delete__()
の任意の組合せを定義することができます。 __get__()
が定義されない場合には、その属性にアクセスすると、そのオブジェクトのインスタンス辞書にその値がある場合を除けば、デスクリプタオブジェクト自身が返ってきます。デスクリプタが __set__()
と __delete__()
またはそのどちらかを定義していれば、データデスクリプタとなります; もし両方とも定義しなければ、非データデスクリプタです。通常、データデスクリプタでは、 __get__()
と __set__()
を定義し、一方、非データデスクリプタには __get__()
メソッドしかありません。 __set__()
と __get__()
を定義したデータデスクリプタは、インスタンス辞書内で属性値が再定義されても、常にこの値をオーバライドします。対照的に、非データデスクリプタの場合には、属性値はインスタンス側でオーバライドされます。
(staticmethod()
や classmethod()
を含む) Python メソッドは、非データデスクリプタとして実装されています。その結果、インスタンスではメソッドを再定義したりオーバライドできます。このことにより、個々のインスタンスが同じクラスの他のインスタンスと互いに異なる動作を獲得することができます。
property()
関数はデータデスクリプタとして実装されています。従って、インスタンスはあるプロパティの動作をオーバライドすることができません。
3.4.2.4. __slots__¶
デフォルトでは、新旧どちらのクラスも、属性の記憶領域として使うための辞書を持っています。この仕様は、ほとんどインスタンス変数を持たないようなオブジェクトの場合には記憶領域の無駄遣いになります。記憶領域の消費量は、大量のインスタンスを生成する際には深刻です。
このデフォルトの設定は、新たな形式のクラス定義において __slots__ を定義することでオーバライドできます。 __slots_ 宣言はインスタンス変数のシーケンスを受け取ります。各々のインスタンス上には、各変数の値を記憶するのにちょうど必要な量だけの記憶領域を確保します。各々のインスタンスに対して __dict__ が生成されることがないので、記憶領域が節約されます。
-
__slots__
¶ このクラス変数には、文字列、反復可能オブジェクト、あるいはインスタンスが用いる変数名を表す文字列からなるシーケンスを代入することができます。この変数が新しい形式のクラスで定義されている場合、 __slots__ は、各インスタンスに対して宣言された変数に必要な記憶領域を確保し、 __dict__ と __weakref__ が自動的に生成されないようにします。
バージョン 2.2 で追加.
__slots__ を利用する際の注意
__slots__ を持たないクラスから継承する場合、 __dict__ 属性は常にアクセス可能なので、サブクラスで __slots__ を定義しても意味がありません。
__dict__ 変数がない場合、 __slots__ に列挙されていない新たな変数をインスタンスに代入することはできません。列挙されていない変数名を使って代入しようとした場合、
AttributeError
が送出されます。新たな変数を動的に代入したいのなら、 __slots__ を宣言する際に'__dict__'
を変数名のシーケンスに追加してください。バージョン 2.3 で変更: これまでは、
'__dict__'
を __slots__ 宣言に追加しても、インスタンス変数名として他にリストされていない新たな属性の代入はできませんでした。__slots__ を定義しているクラスの各インスタンスに __weakref__ 変数がない場合、インスタンスに対する弱参照 (weak reference) はサポートされません。弱参照のサポートが必要なら、 __slots__ を宣言する際に
'__weakref__'
を変数名のシーケンスに追加してください。バージョン 2.3 で変更: これまでは、
'__weakref__'
を __slots__ 宣言に追加しても、弱参照のサポートを有効にできませんでした。__slots__ は、クラスのレベルで各変数に対するデスクリプタ (デスクリプタ (descriptor) の実装 を参照) を使って実装されます。その結果、 __slots__ に定義されているインスタンス変数のデフォルト値はクラス属性を使って設定できなくなっています; そうしないと、デスクリプタによる代入をクラス属性が上書きしてしまうからです。
__slots__ 宣言が動作するのは、定義が行われたクラスだけに限られています。その結果、サブクラスでは、 __slots__ を定義しない限り __dict__ を持つことになります。
あるクラスで、基底クラスですでに定義されているスロットを定義した場合、基底クラスのスロットで定義されているインスタンス変数は (デスクリプタを基底クラスから直接取得しない限り) アクセスできなくなります。これにより、プログラムの趣意が不定になってしまいます。将来は、この問題を避けるために何らかのチェックが追加されるかもしれません。
空でない __slots__ は、
long
、str
、およびtuple
といった、"可変長 (variable-length)" の組み込み型から派生したクラスでは動作しません。__slots__ には、文字列でない反復可能オブジェクトを代入することができます。辞書型も使うことができます; しかし将来、辞書の各キーに相当する値に何らかの特殊な意味が割り当てられるかもしれません。
__class__ への代入は、両方のクラスが同じ __slots__ を持っているときのみ動作します。
バージョン 2.6 で変更: 以前は、新旧どちらかのクラスが __slots__ を持っていたら __class__ への代入はエラーを発生していました。
3.4.3. クラス生成をカスタマイズする¶
デフォルトでは、新スタイルクラスは type()
を使って構築されます。クラス定義が別の名前空間に読み込まれ、クラス名は type(name, bases, dict)
の結果に結合されます。
クラス定義が読み込まれる際、 __metaclass__ が定義されていれば、 type()
の代わりに __metaclass__ が指している呼び出し可能オブジェクトが呼び出されます。これによって、
クラスが生成される前にクラス辞書を変更する
他のクラスのインスタンスを返す -- 本質的にはファクトリ関数の役割を果たす
これらのステップは、メタクラスの __new__()
メソッドで実行されなければなりません。 -- このメソッドから他の属性を持ったクラスを作るには、 type.__new__()
を呼び出すことができます。次の例ではクラスを生成する前に新しい要素をクラス辞書に追加しています。
class metacls(type):
def __new__(mcs, name, bases, dict):
dict['foo'] = 'metacls was here'
return type.__new__(mcs, name, bases, dict)
もちろん、他のクラスメソッドをオーバーライドする(または新しいメソッドを追加する)こともできます。例えば、カスタムの __call__()
メソッドをメタクラスに定義して、新しいインスタンスを常には造らないといったカスタムの動作を実装できます。
-
__metaclass__
¶ この変数は
name
、bases
、およびdict
を引数として取るような任意の呼び出し可能オブジェクトにできます。クラス生成の際、組み込みのtype()
の代わりに、指定された呼び出しオブジェクトが呼び出されます。バージョン 2.2 で追加.
以下に優先順で並んだ規則によって、適切なメタクラスが決定されます:
dict['__metaclass__']
があればそれを使います。それ以外の場合で、最低でも一つ基底クラスを持っているなら、基底クラスのメタクラス (__class__ 属性を探し、なければ基底クラスの型) を使います。
それ以外の場合で、__metaclass__ という名前のグローバル変数があれば、それをつかいます。
それ以外の場合には、旧スタイルのメタクラス (types.ClassType) を使います。
メタクラスは限りない潜在的利用価値を持っています。これまで試されてきたアイデアには、ログ記録、インタフェースのチェック、自動デリゲーション、自動プロパティ生成、プロキシ、フレームワーク、そして自動リソースロック/同期といったものがあります。
3.4.4. インスタンスのカスタマイズとサブクラスチェック¶
バージョン 2.6 で追加.
以下のメソッドは組み込み関数 isinstance()
と issubclass()
のデフォルトの動作を上書きするのに利用します。
特に、 abc.ABCMeta
メタクラスは、抽象基底クラス (ABCs) を"仮想基底クラス (virtual base classes)" として、他の ABC を含む、任意のクラスや (組み込み型を含む) 型に追加するために、これらのメソッドを実装しています。
-
class.
__instancecheck__
(self, instance)¶ instance が (直接、または間接的に) class のインスタンスと考えられる場合に true を返します。定義されていれば、
isinstance(instance, class)
の実装のために呼び出されます。
-
class.
__subclasscheck__
(self, subclass)¶ subclass が (直接、または間接的に) class のサブクラスと考えられる場合に true を返します。定義されていれば、
issubclass(subclass, class)
の実装のために呼び出されます。
なお、これらのメソッドは、クラスの型 (メタクラス) 上で検索されます。実際のクラスにクラスメソッドとして定義することはできません。これは、インスタンスそれ自体がクラスであるこの場合にのみ、インスタンスに呼び出される特殊メソッドの検索と一貫しています。
参考
- PEP 3119 - 抽象基底クラスの導入
抽象基底クラス (
abc
モジュールを参照) を言語に追加する文脈においての動機から、__instancecheck__()
と__subclasscheck__()
を通して、isinstance()
とissubclass()
に独自の動作をさせるための仕様の記述があります。
3.4.5. 呼び出し可能オブジェクトをエミュレートする¶
-
object.
__call__
(self[, args...])¶ インスタンスが関数として "呼ばれた" 際に呼び出されます; このメソッドが定義されている場合、
x(arg1, arg2, ...)
はx.__call__(arg1, arg2, ...)
を短く書いたものになります。
3.4.6. コンテナをエミュレートする¶
以下のメソッドを定義して、コンテナオブジェクトを実装することができます。コンテナは通常、(リストやタプルのような) シーケンスや、(辞書のような) マップ型を指しますが、他のコンテナも同じように表現することができます。最初の一連のメソッドは、シーケンスをエミュレートしたり、マップ型をエミュレートするために使われます; その違いとして、シーケンスの場合には、キーとして許されているのが、シーケンスの長さが N であるときの 0 <= k < N
なる整数 k か、あるいは要素の範囲を表すスライスオブジェクトでなければならないということです。 (後方互換性のため、 __getslice__()
(以下参照) を定義して、拡張されていない単純なスライスを扱うようにもできます。)変更可能なシーケンスでは、Python の標準リストオブジェクトのように、メソッド append()
, count()
, index()
, extend()
, insert()
, pop()
, remove()
, reverse()
,および sort()
を提供しなければなりません。マップ型でも、Python の標準辞書オブジェクトのように、 keys()
, values()
, items()
, has_key()
, get()
, clear()
, setdefault()
, iterkeys()
, itervalues()
, iteritems()
, pop()
, popitem()
, copy()
,および update()
といったメソッドをマップ型で提供するよう推奨しています。 UserDict
モジュールでは、これらのメソッドを __getitem__()
, __setitem__()
, __delitem__()
,および keys()
といった基本セットから作成する上で役に立つ DictMixin
クラスを提供しています。最後に、シーケンス型では以下に述べるメソッド群 __add__()
, __radd__()
, __iadd__()
, __mul__()
, __rmul__()
,および __imul__()
を定義して、 (シーケンス間の結合を意味する) 加算操作と (要素の繰り返しを意味する) 乗算操作を実装しなければなりません; __coerce__()
や、その他の数値演算子を定義してはなりません。マップでもシーケンスでも、 in
演算子が有効利用できるように __contains__()
メソッドの定義を推奨します; マップ型では、 in
は has_key()
と等価でなければなりません; シーケンスでは、シーケンス内の値にわたって検索を行わなければなりません。さらに、マップでもシーケンスでも、コンテナ内にわたる反復操作ができるようにするため、 __iter__()
を実装するよう勧めます; マップ型の場合、 __iter__()
は iterkeys()
と等価でなければなりません; シーケンスの場合、シーケンス内の値にわたって反復操作を行わなければなりません。
-
object.
__len__
(self)¶ 組み込み関数
len()
を実現するために呼び出されます。オブジェクトの長さを>=
0 である整数で返さなければなりません。また、オブジェクトが__nonzero__()
メソッドを定義しておらず、__len__()
メソッドがゼロを返す場合には、ブール演算コンテキストでは偽であるとみなされます。CPython では、オブジェクトの長さは最大でも
sys.maxsize
であることが要求されます。 長さがsys.maxsize
を越える場合、(len()
のような) いくつかの機能はOverflowError
を送出するでしょう。 真偽値としての判定でOverflowError
を送出しないようにするには、オブジェクトは meth:__nonzero__ メソッドを定義していなければなりません。
-
object.
__getitem__
(self, key)¶ self[key]
の値評価 (evaluation) を実現するために呼び出されます。シーケンスの場合、キーとして整数とスライスオブジェクトを受理できなければなりません。 (シーケンス型をエミュレートする場合) 負のインデクスの解釈は__getitem__()
メソッド次第となります。 key が不適切な型であった場合、TypeError
を送出してもかまいません; (負のインデクス値に対して何らかの解釈を行った上で) key がシーケンスのインデクス集合外の値である場合、IndexError
を送出しなければなりません。マップ型の場合は、 key に誤りがある場合(コンテナに含まれていない場合)、KeyError
を送出しなければなりません。注釈
for
ループでは、シーケンスの終端を正しく検出できるようにするために、不正なインデクスに対してIndexError
が送出されるものと期待しています。
-
object.
__setitem__
(self, key, value)¶ self[key]
に対する代入を実現するために呼び出されます。__getitem__()
と同じ注意事項があてはまります。このメソッドを実装できるのは、あるキーに対する値の変更をサポートしているか、新たなキーを追加できるようなマップの場合と、ある要素を置き換えることができるシーケンスの場合だけです。不正な key に対しては、__getitem__()
メソッドと同様の例外の送出を行わなければなりません。
-
object.
__delitem__
(self, key)¶ self[key]
の削除を実現するために呼び出されます。__getitem__()
と同じ注意事項があてはまります。このメソッドを実装できるのは、キーの削除をサポートしているマップの場合と、要素を削除できるシーケンスの場合だけです。不正な key に対しては、__getitem__()
メソッドと同様の例外の送出を行わなければなりません。
-
object.
__missing__
(self, key)¶ self[key]
の実装において辞書内にキーが存在しなかった場合に、 dict のサブクラスのためにdict
.__getitem__()
によって呼び出されます。
-
object.
__iter__
(self)¶ このメソッドは、コンテナに対してイテレータが要求された際に呼び出されます。このメソッドは、コンテナ内の全てのオブジェクトにわたる反復処理ができるような、新たなイテレータオブジェクトを返さなければなりません。マップの場合、コンテナ内のキーに渡る反復処理でなければならず、かつ
iterkeys()
によって利用できなければなりません。イテレータオブジェクトでもこのメソッドを実装する必要があります; イテレータの場合、自分自身を返さなければなりません。イテレータオブジェクトに関するより詳細な情報は、 イテレータ型 を参照してください。
-
object.
__reversed__
(self)¶ reversed()
組み込み関数が逆方向イテレーションを実装するために、(存在すれば)呼び出します。コンテナ内の全要素を逆順にイテレートする、新しいイテレータを返すべきです。__reversed__()
メソッドが定義されていない場合、reversed()
組込み関数は sequence プロトコル (__len__()
と__getitem__()
) を使った方法にフォールバックします。 sequence プロトコルをサポートしたオブジェクトは、reversed()
よりも効率のいい実装を提供できる場合にのみ__reversed__()
を定義するべきです。バージョン 2.6 で追加.
メンバシップテスト演算子 (in
および not in
) は通常、シーケンスに渡る反復処理を使って実装されます。しかし、コンテナオブジェクトで以下の特殊メソッドを定義して、より効率的な実装を行ったり、オブジェクトがシーケンスでなくてもよいようにできます。
-
object.
__contains__
(self, item)¶ メンバシップテスト演算を実現するために呼び出されます。 item が self 内に存在する場合には真を、そうでない場合には偽を返さなければなりません。マップオブジェクトの場合、値やキーと値の組ではなく、キーに対するメンバシップテストを考えなければなりません。
__contains__()
を定義しないオブジェクトに対しては、メンバシップテストはまず、__iter__()
を使った反復を試みます、次に古いシーケンス反復プロトコル__getitem__()
を使います、 言語レファレンスのこの節 を参照して下さい。
3.4.7. シーケンス型エミュレーションで使われるその他のメソッド¶
以下のオプションとなるメソッドを定義して、シーケンスオブジェクトをより高度にエミュレーションできます。変更不能なシーケンスのメソッドでは、 __getslice__()
が定義できるだけです; 変更可能なシーケンスでは三つのメソッド全てを定義できます。
-
object.
__getslice__
(self, i, j)¶ バージョン 2.0 で非推奨: スライスオブジェクトは
__getitem__()
メソッドのパラメタとしてサポートするようになりました。 (しかし、現在の CPython はいまだに__getslice__()
を実装しています。なので、派生クラスでスライスを実装する場合は、このメソッドをオーバーライドしなければなりません。)self[i:j]
の値評価を実現するために呼び出されます。返されるオブジェクトは self と同じ型でなければなりません。スライス表記で i や j がない場合には、それぞれゼロやsys.maxsize
に置き換えられるので注意してください。スライスに負のインデクスが用いられた場合、シーケンスの長さがインデクス値に加算されます。インスタンスが__len__()
メソッドを実装していない場合には、AttributeError
が送出されます。この計算の結果、インデクス値が負でなくなるという保証はありません。シーケンスの長さよりも大きなインデクス値は修正されません。__getslice__()
が定義されていない場合、代わりにスライスオブジェクトが生成されて__getitem__()
に渡されます。
-
object.
__setslice__
(self, i, j, sequence)¶ self[i:j]
への代入を実現するために呼び出されます。 i および j に関しては、__getslice__()
と同じ注釈があてはまります。このメソッドは撤廃されています。
__setslice__()
がないか、self[i:j:k]
形式の拡張スライスの場合には、__setslice__()
が呼ばれる代わりにスライスオブジェクトが生成され、__setitem__()
に渡されます。
-
object.
__delslice__
(self, i, j)¶ self[i:j]
の削除を実現するために呼び出されます。 i および j に関しては、__getslice__()
と同じ注釈があてはまります。このメソッドは撤廃されています。__delslice__()
がないか、self[i:j:k]
形式の拡張スライスの場合には、__delslice__()
が呼ばれる代わりにスライスオブジェクトが生成され、__delitem__()
に渡されます。
これらのメソッドは、単一のコロンを使った単一のスライスで、かつスライスメソッドが利用できるときにだけ呼び出されることに注意してください。拡張スライス表記を含んでいるスライス表記や、スライスメソッドがない場合、 __getitem__()
、 __setitem__()
、あるいは __delitem__()
がスライスオブジェクトを引数として呼び出されます。
以下の例は、プログラムやモジュールを以前のバージョンの Python に対して互換性を持たせる方法を示したものです (__getitem__()
、 __setitem__()
、および __delitem__()
は引数としてスライスオブジェクトをサポートするものと仮定します):
class MyClass:
...
def __getitem__(self, index):
...
def __setitem__(self, index, value):
...
def __delitem__(self, index):
...
if sys.version_info < (2, 0):
# They won't be defined if version is at least 2.0 final
def __getslice__(self, i, j):
return self[max(0, i):max(0, j):]
def __setslice__(self, i, j, seq):
self[max(0, i):max(0, j):] = seq
def __delslice__(self, i, j):
del self[max(0, i):max(0, j):]
...
max()
を呼び出していることに注意してください; この呼び出し __*slice__()
メソッド呼び出される前に、負のインデクス値を処理しておくために必要です。負のインデクス値が使われた場合、 __*item__()
メソッドは与えられた値をそのまま使いますが、 __*slice__()
メソッドは "調理済みの (cooked)" 形式になったインデクス値を受け取ります。負のインデクス値が使われると、メソッドを呼び出す前に、常にシーケンスの長さをインデクス値に加算します (加算してもまだ負の値となっていてもかまいません); これは、組み込みシーケンス型における慣習的な負のインデクス処理方法で、 __*item__()
メソッドでも同様の処理を行うよう期待しています。しかし、ここではすでに負のインデクス値の処理を行っているので、負のインデクスを渡すべきではありません; インデクス値は、 __*item__()
メソッドに渡される前に、シーケンスのインデクス集合の境界に制限されていなければなりません。 max(0, i)
を呼び出せば、適切な値を返すので便利です。
3.4.8. 数値型をエミュレーションする¶
以下のメソッドを定義して、数値型オブジェクトをエミュレートすることができます。特定の種類の数値型ではサポートされていないような演算に対応するメソッド (非整数の数値に対するビット単位演算など) は、未定義のままにしておかなければなりません。
-
object.
__add__
(self, other)¶ -
object.
__sub__
(self, other)¶ -
object.
__mul__
(self, other)¶ -
object.
__floordiv__
(self, other)¶ -
object.
__mod__
(self, other)¶ -
object.
__divmod__
(self, other)¶ -
object.
__pow__
(self, other[, modulo])¶ -
object.
__lshift__
(self, other)¶ -
object.
__rshift__
(self, other)¶ -
object.
__and__
(self, other)¶ -
object.
__xor__
(self, other)¶ -
object.
__or__
(self, other)¶ これらのメソッドは、二項算術演算 (
+
,-
,*
,//
,%
,divmod()
,pow()
,**
,<<
,>>
,&
,^
,|
) を実現するために呼び出されます。例えば、式x + y
の場合、 x が__add__()
メソッドをもつクラスのインスタンスであれば、x.__add__(y)
が呼び出されます。__divmod__()
メソッドは、__floordiv__()
と__mod__()
を使った場合と等価にならなければなりません;__truediv__()
(下記参照) と関連づける必要はありません。組み込みの三項演算子バージョンの関数pow()
をサポートする場合には、__pow__()
は、オプションとなる第三の引数を受け取れなくてはなりません。こらのメソッドが渡された引き数に対する操作を提供していない場合には、
NotImplemented
を送出しなければなりません。
-
object.
__div__
(self, other)¶ -
object.
__truediv__
(self, other)¶ 除算演算 (
/
) は、これらのメソッドで実現されています。__truediv__()
は、__future__.division
が有効であるときに使われます。それ以外の場合には__div__()
が使われますs。二つのメソッドのうち一方しか定義されていなければ、オブジェクトは他方の演算コンテキストをサポートしなくなります; このとき、TypeError
が送出されます。
-
object.
__radd__
(self, other)¶ -
object.
__rsub__
(self, other)¶ -
object.
__rmul__
(self, other)¶ -
object.
__rdiv__
(self, other)¶ -
object.
__rtruediv__
(self, other)¶ -
object.
__rfloordiv__
(self, other)¶ -
object.
__rmod__
(self, other)¶ -
object.
__rdivmod__
(self, other)¶ -
object.
__rpow__
(self, other)¶ -
object.
__rlshift__
(self, other)¶ -
object.
__rrshift__
(self, other)¶ -
object.
__rand__
(self, other)¶ -
object.
__rxor__
(self, other)¶ -
object.
__ror__
(self, other)¶ これらのメソッドは二項算術演算 (
+
,-
,*
,/
,%
,divmod()
,pow()
,**
,<<
,>>
,&
,^
,|
) を実現しますが、メソッド呼び出しが行われる被演算子が逆転して (reflected, swapped: 入れ替えられて) います。これらの関数は、左側の被演算子が対応する演算をサポートしておらずかつ両者の演算子が異なる場合にのみ呼び出されます。 2 例えば、x - y
の式を評価する場合、 y が__rsub__()
メソッドを持つクラスのインスタンスであって、しかもx.__sub__(y)
が NotImplemented を返す場合には、y.__rsub__(x)
が呼び出されます。ただし、三項演算子
pow()
が__rpow__()
を呼ぶことはないので注意してください (型強制の規則が非常に難解になるからです)。注釈
右側の被演算子の型が左側の被演算子の型のサブクラスであり、このサブクラスであるメソッドに対する逆転メソッドが定義されている場合には、左側の被演算子の非逆転メソッドが呼ばれる前に、このメソッドが呼ばれます。この振る舞いにより、サブクラスが親の操作をオーバーライドすることが可能になります。
-
object.
__iadd__
(self, other)¶ -
object.
__isub__
(self, other)¶ -
object.
__imul__
(self, other)¶ -
object.
__idiv__
(self, other)¶ -
object.
__itruediv__
(self, other)¶ -
object.
__ifloordiv__
(self, other)¶ -
object.
__imod__
(self, other)¶ -
object.
__ipow__
(self, other[, modulo])¶ -
object.
__ilshift__
(self, other)¶ -
object.
__irshift__
(self, other)¶ -
object.
__iand__
(self, other)¶ -
object.
__ixor__
(self, other)¶ -
object.
__ior__
(self, other)¶ これらのメソッドは、累算算術代入 (augmented arithmetic assignments,
+=
,-=
,*=
,/=
,//=
,%=
,**=
,<<=
,>>=
,&=
,^=
,|=
) を実現するために呼び出されます。これらのメソッドは、演算をその場で(self を変更する形で) 行うよう試み、その結果(変更された self またはその代わりのもの)を返さなければなりません。特定のメソッドが定義されていない場合、その累算算術演算は通常のメソッドで代用されます。例えば、x += y
を評価する際、 x が__iadd__()
メソッドを持つクラスのインスタンスであれば、x.__iadd__(y)
が呼び出されます。逆に、 x が__iadd()
メソッドを持たないクラスのインスタンスであれば、x + y
の評価と同じようにx.__add__(y)
およびy.__radd__(x)
を考慮します。
-
object.
__neg__
(self)¶ -
object.
__pos__
(self)¶ -
object.
__abs__
(self)¶ -
object.
__invert__
(self)¶ 単項算術演算 (
-
,+
,abs()
および~
) を実現するために呼び出されます。
-
object.
__complex__
(self)¶ -
object.
__int__
(self)¶ -
object.
__long__
(self)¶ -
object.
__float__
(self)¶ 組み込み関数
complex()
,int()
,long()
, およびfloat()
を実現するために呼び出されます。適切な型の値を返さなければなりません。
-
object.
__index__
(self)¶ operator.index()
を実装するために呼び出されます。また、(スライシング)のように Python が整数オブジェクトを必要とする場合には何処でも呼び出されます。整数(int もしくは long)を返す必要があります。バージョン 2.5 で追加.
-
object.
__coerce__
(self, other)¶ "型混合モード (mixed-mode)" での数値間の算術演算を実現するために呼び出されます。 self と other を共通の数値型に変換して、 2 要素のタプルにして返すか、不可能な場合には
None
を返さなければなりません。共通の型がother
の型になる場合、None
を返すだけで十分です。この場合、インタプリタはもう一方のオブジェクトを調べて型強制を行おうとするからです (とはいえ、もう一方の値の型が実装上変更できない場合には、ここで self を other の型に変換しておいた方が便利です)。戻り値にNotImplemented
を使うのは、None
を返すのと同じです。
3.4.9. 型強制規則 (coercion rule)¶
本節では、型強制 (coercion) に関する規則について記述します。プログラム言語が進化するにつれ、型強制規則について正確に記述するのは難しくなってゆきます; 従って、あるバージョンのある実装について記述するのは望ましくありません。その代わりに、型強制に関する非公式的なガイドラインを示しておきます。 Python 3 からは、型強制がサポートされなくなる予定です。
% 演算子の左被演算子が文字列か Unicode オブジェクトの場合、型強制は起きず、文字列としての書式化操作が呼び出されます。
型強制演算の定義はもはや推奨されていません。型強制を定義していない混合型 (mixed-mode) 演算は、もとの引数をそのまま演算操作に渡すようになっています。
新しい形式のクラス (
object
から派生したもの) が、二項演算子に対して__coerce__()
メソッドを呼び出すことはありません。;__coerce__()
が呼び出されるのは、組み込み関数coerce()
が呼び出されたときだけです。事実上、
NotImplemented
を返す演算子は、全く実装されていないものとして扱われます。以下の説明では、
__op__()
および__rop__()
は、演算子に相当する一般的なメソッド名を表すために使われます;__iop__()
はインプレース演算子を表します。例えば、演算子 '+
' の場合、__add__()
および__radd__()
がそれぞれ左右の被演算子用の二項演算子として使われ、__iadd__()
がインプレース演算用の演算子として使われる、といった具合です。オブジェクト x および y に対して、まず
x.__op__(y)
が試されます。この演算が実装されていないか、NotImplemented
を返す場合、次にy.__rop__(x)
が試されます。この演算も実装されていないか、NotImplemented
を返すなら、TypeError
例外が送出されます。ただし、以下の例外があるので参照してください:前項に対する例外: 左被演算子が組み込み型や新スタイルクラスのインスタンスであり、かつ右被演算子が左被演算子と同じクラスか適切なサブクラスのインスタンスであり、さらに親クラスの
__rop__()
メソッドをオーバライドしている場合、左被演算子の__op__()
メソッドを試す 前に 右被演算子の__rop__()
が試されます。これは、サブクラス側で二項演算子を完全にオーバライドできるようにするためです。そうしなければ、常に左被演算子の
__op__()
メソッドが右被演算子を受理してしまいます: あるクラスのインスタンスが被演算子になるとされている場合、そのサブクラスのインスタンスもまた受理可能だからです。双方の被演算子が型強制を定義している場合、型強制は被演算子の型の
__op__()
や__rop__()
メソッドが呼び出される前に呼び出され、それより早くなることはありません。型強制の結果、型強制を行うことになったいずれの被演算子とも異なる型が返された場合、返されたオブジェクトの新たな型を使って、この過程が部分的に再度行われます。('
+=
' のような) インプレース型の演算子を用いる際、左被演算子が__iop__()
を実装していれば、__iop__()
が呼び出され、型強制は一切行われません。演算が__op__()
かつ/または__rop__()
に帰着した場合、通常の型強制規則が適用されます。x + y
において、 x が結合 (concatenation) 演算を実装しているシーケンスであれば、シーケンスの結合が実行されます。x * y
において、一方の演算子が繰り返し (repeat) 演算を実装しているシーケンスであり、かつ他方が整数 (int
またはlong
) である場合、シーケンスの繰り返しが実行されます。(
__eq__()
などのメソッドで実装されている) 拡張比較は、決して型強制を行いません。(__cmp__()
で実装されている) 三値比較 (three-way comparison) は、他の二項演算子で行われているのと同じ条件で型強制を受けます。現在の実装では、組み込み数値型
int
,long
,float
およびcomplex
は型強制を行いません; これらの型は全て、関数coerce()
から利用するための__coerce__()
メソッドを実装しています。バージョン 2.7 で変更: 複素数型は、型混合の二項算術演算に
__coerce__()
を暗示的に呼び出さなくなりました。
3.4.10. with文とコンテキストマネージャ¶
バージョン 2.5 で追加.
コンテキストマネージャ(context manager) とは、 with
文の実行時にランタイムコンテキストを定義するオブジェクトです。コンテキストマネージャは、コードブロックを実行するために必要な入り口および出口の処理を扱います。コンテキストマネージャは通常、 with
文( with 文 の章を参照)により起動されますが、これらのメソッドを直接呼び出すことで起動することもできます。
コンテキストマネージャの代表的な使い方としては、様々なグローバル情報の保存および更新、リソースのロックとアンロック、ファイルのオープンとクローズなどが挙げられます。
コンテキストマネージャについてのさらなる情報については、 コンテキストマネージャ型 を参照してください。
-
object.
__exit__
(self, exc_type, exc_value, traceback)¶ コンテキストマネージャの出口で実行される処理です。パラメータは、コンテキストが終了した原因となった例外について説明しています。コンテキストが例外を送出せず終了した場合は、全ての引き数に
None
が設定されます。もし、例外が送出され、かつメソッドが例外を抑制したい場合(すなわち、例外が伝播されるのを防ぎたい場合)、このメソッドは True を返す必要があります。そうでなければ、このメソッドの終了後、例外は通常通り伝播することになります。
__exit__()
メソッドは受け取った例外を再度送出すべきではありません。これは、呼び出し側の責任でおこなってください。
3.4.11. 旧スタイルクラスの特殊メソッド検索¶
旧スタイルクラスにおいて、特殊メソッドは常に他のメソッドや属性と同じ方法で検索されます。これは、メソッドが x.__getitem__(i)
のように明示的に検索された時も、 x[i]
のように暗黙的に検索された時も同じです。
これにより、1つの旧スタイルクラスの異なるインスタンスが、それぞれ別の適切な特殊属性を持っている場合、異なる動作をすることになります。
>>> class C:
... pass
...
>>> c1 = C()
>>> c2 = C()
>>> c1.__len__ = lambda: 5
>>> c2.__len__ = lambda: 9
>>> len(c1)
5
>>> len(c2)
9
3.4.12. 新スタイルクラスの特殊メソッド検索¶
新スタイルクラスでは、特殊メソッドの暗黙的な呼び出しは、オブジェクトインスタンスの辞書ではなく、 type の辞書で定義されているときにのみ正しく動作することが保証されます。この動作は、以下のコードが(旧スタイルクラスの同等な例と異なり)例外を発生させる理由です。
>>> class C(object):
... pass
...
>>> c = C()
>>> c.__len__ = lambda: 5
>>> len(c)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: object of type 'C' has no len()
この動作の背景となる理由は、 __hash__()
と __repr__()
といった type オブジェクトを含むすべてのオブジェクトで定義されている特殊メソッドにあります。これらのメソッドの暗黙の検索が通常の検索プロセスを使った場合、 type オブジェクト自体に対して実行されたときに失敗してしまいます:
>>> 1 .__hash__() == hash(1)
True
>>> int.__hash__() == hash(int)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: descriptor '__hash__' of 'int' object needs an argument
クラスの非結合メソッドをこのようにして実行しようとすることは、'metaclass confusion' と呼ばれることもあり、特殊メソッドを検索するときはインスタンスをバイパスすることで回避されます:
>>> type(1).__hash__(1) == hash(1)
True
>>> type(int).__hash__(int) == hash(int)
True
正確性のためにインスタンス属性をスキップするのに加えて、特殊メソッド検索はオブジェクトのメタクラスを含めて、 __getattribute__()
メソッドもバイパスします:
>>> class Meta(type):
... def __getattribute__(*args):
... print "Metaclass getattribute invoked"
... return type.__getattribute__(*args)
...
>>> class C(object):
... __metaclass__ = Meta
... def __len__(self):
... return 10
... def __getattribute__(*args):
... print "Class getattribute invoked"
... return object.__getattribute__(*args)
...
>>> c = C()
>>> c.__len__() # Explicit lookup via instance
Class getattribute invoked
10
>>> type(c).__len__(c) # Explicit lookup via type
Metaclass getattribute invoked
10
>>> len(c) # Implicit lookup
10
このように __getattribute__()
機構をバイパスすることで、特殊メソッドの扱いに関するある程度の自由度と引き換えに (特殊メソッドはインタプリタから一貫して実行されるためにクラスオブジェクトに設定 しなければならない)、インタープリタを高速化するための大きな余地が手に入ります。
注記