2016-10-13 29 views
9

Tôi đã tìm kiếm một cách tổng quát để so sánh hai số trong Python. Đặc biệt, tôi muốn tìm hiểu xem họ có giống nhau hay không.Cách tổng quát để so sánh các số trong Python

Các loại số bằng Python là:

int, long, float & complex 

Ví dụ, tôi có thể so sánh 2 số nguyên (một loại số) bằng cách đơn giản nói:

a == b 

Đối với phao nổi, chúng ta phải cẩn thận hơn do làm tròn độ chính xác, nhưng tôi có thể so sánh chúng trong một số dung sai.

Câu hỏi

Chúng tôi được 2 numerics chung ab: Làm thế nào để chúng ta so sánh chúng? Tôi đã nghĩ đến việc đúc cả hai để phức tạp (mà sau đó sẽ có một phần 0 tưởng tượng nếu loại là, nói, int) và so sánh trong tên miền đó?

Câu hỏi này tổng quát hơn so với chỉ so sánh trực tiếp phao. Chắc chắn, nó liên quan đến vấn đề này, nhưng nó không giống nhau.

Trả lời

6

Trong Python 3.5 (và trong NumPy), bạn có thể sử dụng isclose

Đọc số PEP 485 mô tả nó, Python 3.5 math library listingnumpy.isclose để biết thêm. Phiên bản gọn gàng hoạt động trong tất cả các phiên bản Python được hỗ trợ.

Ví dụ:

>>> from math import isclose 
>>> isclose(1,1.00000000001) 
True 
>>> isclose(1,1.00001) 
False 

Dung sai tương đối và tuyệt đối có thể được thay đổi.

khoan dung tương đối có thể được coi như + - một tỷ lệ phần trăm giữa hai giá trị:

>>> isclose(100,98.9, rel_tol=0.02) 
True 
>>> isclose(100,97.1, rel_tol=0.02) 
False 

Dung sai tuyệt đối là một giá trị tuyệt đối giữa hai giá trị.Nó giống như kiểm tra của abs(a-b)<=tolerance

Tất cả các loại số Python đều hỗ trợ phiên bản Python 3.5. (Sử dụng phiên bản cmath cho phức tạp)

Tôi nghĩ rằng thuật ngữ dài hơn, đây là đặt cược tốt hơn cho số học. Đối với Python cũ hơn, chỉ cần nhập nguồn. Có phiên bản trên Github.

Hoặc, (ít ưu điểm kiểm tra lỗi và infNaN hỗ trợ), bạn chỉ có thể sử dụng:

def myisclose(a, b, *, rel_tol=1e-09, abs_tol=0.0): 
    return abs(a-b) <= max(rel_tol * max(abs(a), abs(b)), abs_tol) 
+0

+1 cho thư viện GitHub. Như họ nói: Họ ngắn mạch cho sự bình đẳng chính xác, nhưng sau đó nhảy vào một kiểm tra cẩn thận hơn nếu không nghiêm ngặt bình đẳng. Đó là những gì tôi đã suy nghĩ (thậm chí xử lý các loại phức tạp). – denvar

4

Tại sao không chỉ sử dụng ==?

>>1 == (1+0j) 
True 
>>1.0 == 1 
True 

Tôi chắc chắn điều này phù hợp với tất cả các loại số.

+1

Haha, câu trả lời giống hệt nhau :) – brianpck

+1

Nó thậm chí làm việc cho bools - 'Đúng == 1.0' và 'False = = 0.0' cả hai trả về 'True'. –

5

Nếu bạn đang tìm cách so sánh các loại số khác nhau, không có gì sai với toán tử ==: Python sẽ xử lý việc nhập kiểu. Hãy xem xét những điều sau đây:

>>> 1 == 1 + 0j == 1.0 
True 

Trong trường hợp bạn đang làm các phép toán mà có thể dẫn đến việc mất độ chính xác (đặc biệt là với phao), một kỹ thuật phổ biến là để kiểm tra xem các giá trị nằm trong một khoan dung nhất định. Ví dụ:

>>> (10**.5)**2 
10.000000000000002 
>>> (10**.5)**2 == 10 
False 

Trong trường hợp này, bạn có thể tìm giá trị tuyệt đối của sự khác biệt và chắc chắn rằng nó là dưới một ngưỡng nhất định:

>>> abs((10**.5)**2 - 10) < 1e-10 
True 
+0

Tôi đoán mối quan tâm của tôi nảy sinh với sự khoan dung, nó hoạt động như thế nào? – denvar

+1

@denvar Tôi đã thêm một cái gì đó để khoan dung – brianpck

+1

@denvar kiểm tra http://stackoverflow.com/questions/5595425/what-is-the-best-way-to-compare-floats-for-almost-equality-in-python/ 33024979 # 33024979 để so sánh với dung sai. Tôi không nghĩ rằng câu trả lời làm việc với số phức tạp mặc dù. –

Các vấn đề liên quan