Pythonで2つのリストを減算する


84

現在、vector3値がリストとして表されています。これらのようなvector3値の2つを減算する方法はありますか?

[2,2,2] - [1,1,1] = [1,1,1]

タプルを使用する必要がありますか?

それらのどれもこれらの型でこれらのオペランドを定義していない場合、代わりにそれを定義できますか?

そうでない場合は、新しいvector3クラスを作成する必要がありますか?

回答:


134

これが頻繁に実行することになり、さまざまな操作を行う場合は、このようなケースを処理するクラスを作成するか、Numpyなどのライブラリを使用することをお勧めします。

それ以外の場合は、zip組み込み関数で使用されるリスト内包表記を探します。

[a_i - b_i for a_i, b_i in zip(a, b)]

83

リスト内包に代わる方法は次のとおりです。マップはリスト(後者の引数)を繰り返し処理し、同時に実行し、それらの要素を引数として関数(最初の引数)に渡します。結果のリストを返します。

map(operator.sub, a, b)

このコードは構文が少ないため(私にとってはより美的です)、長さ5のリストでは明らかに40%高速です(bobinceのコメントを参照)。それでも、どちらのソリューションでも機能します。


私は通常、リスト内包表記がmap()で推奨されているのを目にしますが、それは見た目がすっきりしたコードだからかもしれません...パフォーマンスの違いがあるかどうかはわかりません。
David Z

2
map()は、5要素の減算のPy2.6で私にとってほぼ40%速くなります。内包表記は、ラムダを回避する方が新しくてクリーンですが、既存の関数をマッピングする場合でも、マップはかなりきれいになります...特にここでは、組み込みのzipを活用できます。
bobince 2009

1
これはarray.arrayでも機能します(結果はリストですが)
gens

5
'importoperator'句が必要です。int .__ sub__はトリックをより良くします))
garej 2017

13

リストがaとbの場合、次のことができます。

map(int.__sub__, a, b)

しかし、おそらくそうすべきではありません。それが何を意味するのか誰にも分かりません。


1
フロートで自分でこれに出くわした。その場合はmap(float.__sub__, a, b)機能します。ヒントをありがとう!
S3DEV

9

NumPyもお勧めします

ベクトル計算を行うのが高速であるだけでなく、便利な関数もたくさんあります。

1Dベクトルに対してさらに高速なものが必要な場合は、vopを試してください

MatLabに似ていますが、無料です。これがあなたがすることの例です

from numpy import matrix
a = matrix((2,2,2))
b = matrix((1,1,1))
ret = a - b
print ret
>> [[1 1 1]]

ブーム。


1
np.arrayより簡単な解決策になります
garej 2017



4

わずかに異なるVectorクラス。

class Vector( object ):
    def __init__(self, *data):
        self.data = data
    def __repr__(self):
        return repr(self.data) 
    def __add__(self, other):
        return tuple( (a+b for a,b in zip(self.data, other.data) ) )  
    def __sub__(self, other):
        return tuple( (a-b for a,b in zip(self.data, other.data) ) )

Vector(1, 2, 3) - Vector(1, 1, 1)

3

単純な複数のライナーを実行することを計画している場合は、独自のクラスを実装し、ケースに適用される適切な演算子をオーバーライドすることをお勧めします。

Pythonの数学からの引用:

class Vector:

  def __init__(self, data):
    self.data = data

  def __repr__(self):
    return repr(self.data)  

  def __add__(self, other):
    data = []
    for j in range(len(self.data)):
      data.append(self.data[j] + other.data[j])
    return Vector(data)  

x = Vector([1, 2, 3])    
print x + x

2

Pycharmでコーディングしていた人にとっては、他の人も復活させます。

 import operator
 Arr1=[1,2,3,45]
 Arr2=[3,4,56,78]
 print(list(map(operator.sub,Arr1,Arr2)))

1

Pythonのと関数の組み合わせはmaplambdaこの種の問題の優れた解決策です。

a = [2,2,2]
b = [1,1,1]
map(lambda x,y: x-y, a,b)

zip @UncleZeivで示されているように、関数はもう1つの良い選択です。


0
arr1=[1,2,3]
arr2=[2,1,3]
ls=[arr2-arr1 for arr1,arr2 in zip(arr1,arr2)]
print(ls)
>>[1,-1,0]

2
このコードスニペットが解決策になる可能性がありますが、説明を含めると、投稿の品質が向上します。あなたは将来読者のために質問に答えていることを忘れないでください、そしてそれらの人々はあなたのコード提案の理由を知らないかもしれません。
ナレンドラジャドハブ2018

0

この回答は、「通常の/簡単に理解できる」pythonicコードの書き方を示しています。

zip誰もが知っているわけではないので、使用しないことをお勧めします。


ソリューションは、リスト内包表記と一般的な組み込み関数を使用します。


代替案1(推奨):

a = [2, 2, 2]
b = [1, 1, 1]
result = [a[i] - b[i] for i in range(len(a))]

Pythonの最も基本的な関数のみを使用するため、推奨されます


代替案2:

a = [2, 2, 2]
b = [1, 1, 1]
result = [x - b[i] for i, x in enumerate(a)]

代替案3(BioCoderが述べたように):

a = [2, 2, 2]
b = [1, 1, 1]
result = list(map(lambda x, y: x - y, a, b))

なぜ反対票を投じるのですか?私の答えはユニークで、他の人の助けになることがあります。
ティミーチャン

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.