2012-05-14 25 views
131

Cách đơn giản nhất để so sánh hai mảng numpy cho bình đẳng là gì (bình đẳng được định nghĩa là: A = B iff cho tất cả các chỉ số i: A[i] == B[i])?So sánh hai mảng numpy cho sự bình đẳng, yếu tố thông minh

Đơn giản chỉ cần sử dụng == mang lại cho tôi một mảng boolean:

>>> numpy.array([1,1,1]) == numpy.array([1,1,1]) 

array([ True, True, True], dtype=bool) 

Tôi có phải and các yếu tố của mảng này để xác định xem các mảng đều bình đẳng, hoặc là có một cách đơn giản hơn để so sánh?

Trả lời

197
(A==B).all() 

kiểm tra nếu tất cả giá trị của mảng (A == B) là True.

Sửa (từ câu trả lời dbaupp và bình luận yoavram của)

Cần lưu ý rằng:

  • giải pháp này có thể có một hành vi kỳ lạ trong một trường hợp cụ thể: nếu một trong hai A hoặc B trống và cái còn lại chứa một phần tử, sau đó nó trả về True. Vì một lý do nào đó, so sánh A==B trả về một mảng trống, mà toán tử all trả về True.
  • Nguy cơ khác là nếu AB không có cùng hình dạng và không phát sóng được thì phương pháp này sẽ gây ra lỗi.

Tóm lại, giải pháp tôi đề xuất là một trong những tiêu chuẩn, tôi nghĩ, nhưng nếu bạn có một nghi ngờ về AB hình dạng hoặc đơn giản chỉ muốn được an toàn: sử dụng một trong những chức năng chuyên ngành:

np.array_equal(A,B) # test if same shape, same elements values 
np.array_equiv(A,B) # test if broadcastable shape, same elements values 
np.allclose(A,B,...) # test if same shape, elements have close enough values 
+7

Bạn hầu như luôn luôn muốn 'IME np.array_equal'. '(A == B) .all()' sẽ ** sụp đổ nếu A và B có độ dài khác nhau **. Kể từ 1,10 numpy, [== tăng cảnh báo không dùng nữa trong trường hợp này] (https://github.com/numpy/numpy/commit/6bf0e419dc79ea6815557c57b7e9bb504ba20543). –

+0

Bạn đã có một điểm tốt, nhưng IME tôi thường biết rằng hình dạng của A và B trước khi tay. Tôi đoán nó phụ thuộc vào bối cảnh, và hương vị tôi đoán. –

64

Giải pháp (A==B).all() rất gọn gàng, nhưng có một số chức năng được tích hợp sẵn cho tác vụ này. Cụ thể là array_equal, allclosearray_equiv.

(Mặc dù, một số thử nghiệm nhanh với timeit dường như chỉ ra rằng phương pháp (A==B).all() là nhanh nhất, đó là một chút đặc biệt, do nó phải phân bổ một mảng hoàn toàn mới.)

+10

bạn nói đúng, ngoại trừ nếu một trong các mảng được so sánh rỗng, bạn sẽ nhận được câu trả lời sai với '(A == B) .all()'. Ví dụ, hãy thử: '(np.array ([1]) == np.array ([])). All()', nó cho 'True', trong khi' np.array_equal (np.array ([1]), np.array ([])) 'cho' Sai' – yoavram

+1

Tôi vừa phát hiện ra sự khác biệt về hiệu năng này. Thật lạ vì nếu bạn có 2 mảng hoàn toàn khác nhau '(a == b) .all()' vẫn còn nhanh hơn 'np.array_equal (a, b)' (có thể vừa kiểm tra một phần tử duy nhất và thoát) . –

+0

'np.array_equal' cũng hoạt động với' danh sách mảng và 'mảng ma trận'. Đây có thể là lý do cho hiệu suất chậm hơn. – TheEspinosa

11

Hãy đo hiệu suất bằng cách sử dụng đoạn mã sau.

import numpy as np 
import time 

exec_time0 = [] 
exec_time1 = [] 
exec_time2 = [] 

sizeOfArray = 5000 
numOfIterations = 200 

for i in xrange(numOfIterations): 

    A = np.random.randint(0,255,(sizeOfArray,sizeOfArray)) 
    B = np.random.randint(0,255,(sizeOfArray,sizeOfArray)) 

    a = time.clock() 
    res = (A==B).all() 
    b = time.clock() 
    exec_time0.append(b - a) 

    a = time.clock() 
    res = np.array_equal(A,B) 
    b = time.clock() 
    exec_time1.append(b - a) 

    a = time.clock() 
    res = np.array_equiv(A,B) 
    b = time.clock() 
    exec_time2.append(b - a) 

print 'Method: (A==B).all(),  ', np.mean(exec_time0) 
print 'Method: np.array_equal(A,B),', np.mean(exec_time1) 
print 'Method: np.array_equiv(A,B),', np.mean(exec_time2) 

Output

Method: (A==B).all(),  0.03031857 
Method: np.array_equal(A,B), 0.030025185 
Method: np.array_equiv(A,B), 0.030141515 

Theo kết quả trên, các phương pháp NumPy dường như nhanh hơn so với sự kết hợp của == điều hành và tất cả() phương pháp và bởi so sánh các phương pháp gumpy nhanh nhất có vẻ là phương pháp numpy.array_equal.

+0

Bạn nên sử dụng kích thước mảng lớn hơn, phải mất ít nhất một giây để biên dịch để tăng độ chính xác của thử nghiệm. –

3

Nếu bạn muốn kiểm tra xem hai mảng có cùng một số shape AND elements, bạn nên sử dụng np.array_equal vì đây là phương pháp được đề xuất trong tài liệu.

Hiệu suất khôn ngoan không mong đợi bất kỳ kiểm tra bình đẳng nào sẽ đánh bại một kiểm tra khác, vì không có nhiều chỗ để tối ưu hóa comparing two elements. Chỉ vì lợi ích, tôi vẫn làm một số xét nghiệm.

import numpy as np 
import timeit 

A = np.zeros((300, 300, 3)) 
B = np.zeros((300, 300, 3)) 
C = np.ones((300, 300, 3)) 

timeit.timeit(stmt='(A==B).all()', setup='from __main__ import A, B', number=10**5) 
timeit.timeit(stmt='np.array_equal(A, B)', setup='from __main__ import A, B, np', number=10**5) 
timeit.timeit(stmt='np.array_equiv(A, B)', setup='from __main__ import A, B, np', number=10**5) 
> 51.5094 
> 52.555 
> 52.761 

Vì vậy, khá nhiều bình đẳng, không cần phải nói về tốc độ.

Các (A==B).all() cư xử khá nhiều như đoạn mã sau:

x = [1,2,3] 
y = [1,2,3] 
print all([True if x[i]==y[i] else False for i in range(len(x))]) 
> True 
Các vấn đề liên quan