実例解析Python中の_unew_特殊な方法

4431 ワード

同前new_方法は何ですか?
類を工場にたとえるとinit_()方法はこの工場の生産労働者です。init_()方法で受ける初期化パラメータは生産に必要な原料であり、__uinit_()方法は方法の語句によって、原料を一例に加工して工場出荷することを担当します。そうしてまたnew_()生産部の社長です。new_()方法は原料を生産部の労働者に提供するかどうかを決定することができます。また、その生産部の製品を出荷するかどうかを決めています。
同前new_()方法の特性:
1.__new_()メソッドは、クラス準備が自身をインスタンス化するときに呼び出します。
2.グウnew_()方法は常にクラスの静的方法であり,静的方法の装飾器を加えなくてもよい。
クラスの実用化とその構造方法は通常このようです。

class MyClass(object):
  def __init__(self, *args, **kwargs):
    ...
#    
myclass = MyClass(*args, **kwargs)
以上のように、一つのクラスは、複数の位置パラメータと複数の命名パラメータを有することができ、例示化が開始された後、__u u_u uを呼び出すことができる。init_()方法の前に、Pythonはまず_u uを呼び出します。new_()方法:

def __new__(cls, *args, **kwargs):
  ...
最初のパラメータclsは、現在実装されているクラスです。
   現在のクラスのインスタンスを取得するには、現在のクラスの__u unew_()メソッド文では、現在のクラスの親タイプの_u u_u uを呼び出します。new_()方法。
例えば、現在のクラスが直接objectから継承されている場合、現在のクラスの_unew_()方法で返したオブジェクトは、

def __new__(cls, *args, **kwargs):
  ...
  return object.__new__(cls)
(注意:
実は(新式)類の中に書き換えがなければnew_()新しいクラスを定義する時に、新しいクラスを定義し直していません。new_()の場合、Pythonはデフォルトではこのクラスの直接の父親類を呼び出すnew_()このような例を作成する方法であり、親類も書き換えられていない場合はnew_()これをそのままに、objectの_u u uにさかのぼります。new_()方法は、Objectがすべての新式のベースですから。)
同前new_方法で受け入れられるパラメータも、_u u u uinit_同じですが、どんぶりですinit_クラスのインスタンスを作成した後に呼び出します。new_このような例を作成する方法です。

# -*- coding: utf-8 -*-

class Person(object):
  """Silly Person"""

  def __new__(cls, name, age):
    print '__new__ called.'
    return super(Person, cls).__new__(cls, name, age)

  def __init__(self, name, age):
    print '__init__ called.'
    self.name = name
    self.age = age

  def __str__(self):
    return '<Person: %s(%s)>' % (self.name, self.age)

if __name__ == '__main__':
  piglei = Person('piglei', 24)
  print piglei

実行結果:

piglei@macbook-pro:blog$ python new_and_init.py
__new__ called.
__init__ called.
<Person: piglei(24)>
このコードを実行することで、私たちは見られます。new_メソッドの呼び出しは、__u uで発生します。init_前の。実際にクラスを具体化する時、具体的な実行ロジックはこうです。

p = Person(name, age)
まず、nameとageパラメータを使用してPersonクラスのu_u_uを実行する。new_方法、これnew_方法は、Personクラスの一例(通常はsuper(Persion,cls)を使用する。new_このようなやり方で
そしてこの例を利用してクラスの_u u u u u u u uを呼び出します。init_方法は、前のステップで中をかきます。new_生まれた例はすなわち_u u u u u u u u uである。init_中のself
だから、チウinit_同前new_一番大きな違いは:
同前init_一般的に、クラスのインスタンスが作成された後に発生するいくつかの追加的な動作を行うために、この初期化のプロセスを制御するために使用される。これはインスタンスレベルの方法です。
同前new_一般的に、新しいインスタンスを生成するプロセスを制御するために使用される。クラスレベルの方法です。
でもこんなにたくさん話しました。new_一番普通の使い方は何ですか?new_?
同前new_の役割
Python公式文書によるとnew_方法は主にいくつかの可変ではないクラスを継承する時(例えば、int、str、tuple)、これらのクラスをカスタマイズするための具体的なプロセスを提供します。また、カスタムのmetaclassを実現します。
まず最初の機能を見てみます。具体的にはintを例として使ってもいいです。
もし我々は常に正の整数タイプである必要があります。統合を通じて、このようなコードを書くことができます。

class PositiveInteger(int):
  def __init__(self, value):
    super(PositiveInteger, self).__init__(self, abs(value))

i = PositiveInteger(-3)
print i

しかし、運行後に発見されます。結果は私たちが考えているほどではないです。これはintこのような可変ではない対象に対して、私達はそれを積載するしかないからです。new_方法はカスタムの役割を果たすことができます。
これは修正されたコードです。

class PositiveInteger(int):
  def __new__(cls, value):
    return super(PositiveInteger, cls).__new__(cls, abs(value))

i = PositiveInteger(-3)
print i

重荷重を通過するnew_方法は、必要な機能を実現しました。
もう一つの役割は、カスタムmetaclassについてです。実は私が一番最初に接触しました。new_というときは、カスタムのmetaclassが必要ですが、紙面の都合上、今度はpythonのmetaclassと_u_u uを話しに来ます。new_という関係です。
ひを使うnew_を実装します
実は、私達が理解した時に。new_方法の後、設計モードの単一例モードを実現するなど、他の面白いことをするためにそれを利用することもできます。
クラスは毎回実装されているので、発生する過程はすべて__u u_u uを通過します。new_コントロールしますので、リロードします。new_方法は単一例モードを簡単に実現できます。

class Singleton(object):
  def __new__(cls):
    #      ,         ,           instance  
    if not hasattr(cls, 'instance'):
      cls.instance = super(Singleton, cls).__new__(cls)
    return cls.instance

obj1 = Singleton()
obj2 = Singleton()

obj1.attr1 = 'value1'
print obj1.attr1, obj2.attr1
print obj1 is obj2

出力結果:

value1 value1
True
obj 1とobj 2は同じ例です。