2016-04-11 6 views

答えて

3

あなたの質問にタグが付いているpython 2.7では、__setslice__のマジックメソッドです。詳細はhere in the datamodel sectionと記載されています。

__setslice__(self, i, j, sequence) 
    Called to implement assignment to self[i:j]. 

これは下位互換性のための古いインターフェイスです。たとえば、L[0:2:](これに相当するはずです)のスライスに割り当てる場合は、実際には__setitem__という新しいインターフェイスを使用します。

フードの下に行くか見て、あなたが独自のクラスを作成し、リストを継承することができます。

>>> class MyList(list): 
...  def __setslice__(self, *args): 
...   print '__setslice__ called with args:', args 
...   list.__setslice__(self, *args) 
...  def __setitem__(self, *args): 
...   print '__setitem__ called with args:', args   
...   list.__setitem__(self, *args) 
...   

はのは、いくつかの例を見てみましょう:渡さ

>>> L = MyList([0, 1, 2, 3, 4]) 
>>> L[0:2] = [5] 
__setslice__ called with args: (0, 2, [5]) 

3つの引数があります常に左と右のエンドポイント、次に割り当ての右側のオブジェクトを選択します。常に__setitem__の新しいインタフェースを介して移動し、sliceオブジェクトのインスタンスを渡すのではなく/ストップインデックスを開始するステップとスライスを使用

>>> L[0:2:] = [5] 
__setitem__ called with args: (slice(0, 2, None), [5]) 

。エンドポイントを省略

>>> L[1:] = [5] 
__setslice__ called with args: (1, 9223372036854775807, [5]) 

sys.maxint使用(開始を省略すると、使用0)。

>>> L[::] = 'potato' 
__setitem__ called with args: (slice(None, None, None), 'potato') 

右側のオブジェクトはリストである必要はありません。

私が言及したい最後のことは、組み込みのリストタイプから派生している場合は__setslice__で悩むだけです。通常あなたはではありません新しいコードを書く場合、近代的な方法はabstract base classを継承することになります。具体的にはcollections.Sequenceはリストのような構造のための明白な選択です。そうすれば、ビルトインリストが下位互換性のために持っているすべてのいぼやハックを心配する必要はありません。

6

これは__setitem__または__setslice__の方法で達成されます。 (__setslice__は、IIRCではなく、python3.xでは削除されています)。リストについて

、表現:

L[start: stop] = some_iterable 

は(非包括的)some_iterableからアイテムを取ると、停止するように最初からインデックスにある要素を置き換えます。だから、あなたのデモコードでは、あなたが持っている:

L[0:2] = [5] 

これは、インデックス01の要素を取り、5に置き換えます。

置き換えリストは、置き換えられるサブリストと同じ長さである必要はありません。

おそらくそれを考えるには良い方法は、次の操作を行うためのインプレース方法として、次のとおりです。

L[a:b] = c 

# equivalent to the following operation (done in place) 
L[:a] + list(c) + L[b:] 

あなたが実際にそれが起こるか好奇心であれば、ソースコードは最高です参照。 PyList_SetSlicelist_ass_sliceを呼び出し、右側の反復可能性をシーケンス(tupleまたはlist IIRC)に変えます。適切な量​​のデータを保持するように配列のサイズを変更し、スライスの右側にあるものを適切な場所にコピーし、新しいデータをコピーします。リストが拡大するか縮小するかによって、いくつかの異なるコードパス(および操​​作の順序)がありますが、それはその基本的な要点です。

+0

ありがとうございました! – SpegooterCode

関連する問題