2016-09-20 37 views
0

我有一個腳本,它貫穿三角形的一組座標,並確定它們是否是直角三角形。其中一部分使用餘弦規則,並且在檢查恰好落在一行中的某組點時遇到了問題。下面是導致問題的一部分:math.acos acos範圍內的數學域錯誤

s1 = math.sqrt(((x2-x1)**2)+((y2-y1)**2)) 
s2 = math.sqrt(((x3-x2)**2)+((y3-y2)**2)) 
s3 = math.sqrt(((x3-x1)**2)+((y3-y1)**2)) 
num1 = (s1**2)+(s2**2)-(s3**2) 
den1 = (2)*(s1)*(s2) 
theta1 = math.acos(num1/den1) 
num2 = (s1**2)+(s3**2)-(s2**2) 
den2 = (2)*(s1)*(s3) 
theta2 = math.acos(num2/den2) 
num3 = (s3**2)+(s2**2)-(s1**2) 
den3 = (2)*(s3)*(s2) 
theta3 = math.acos(num3/den3) 

當我用三點運行此通過([0,0],[4,4],[1,1]),我收到以下錯誤:

Traceback (most recent call last): 
File "./i091.py", line 79, in <module> 
    detect_right_triangle(xy1, xy2, xy3) 
File "./i091.py", line 50, in detect_right_triangle 
    theta2 = math.acos(num2/den2) 
ValueError: math domain error 

只是可以肯定的是我不會餘弦函數的範圍之外,我不得不將其打印theta2的分子和分母爲所有的評定分,並得到這個領導到問題點:

***** [[0, 0], [4, 2], [1, 1]] 
>>> num2 = 12.0 
>>> den2 = 12.6491106407 
***** [[0, 0], [4, 3], [1, 1]] 
>>> num2 = 14.0 
>>> den2 = 14.1421356237 
***** [[0, 0], [4, 4], [1, 1]] 
>>> num2 = 16.0 
>>> den2 = 16.0 

I會認爲有兩個數字是相同的,無論出於何種原因(16.0)都有問題,但對於第二點,它在[2,2]和[3,3]上運行良好:

***** [[0, 0], [2, 2], [1, 1]] 
>>> num2 = 8.0 
>>> den2 = 8.0 

...

***** [[0, 0], [3, 3], [1, 1]] 
>>> num2 = 12.0 
>>> den2 = 12.0 

上什麼可能是錯誤怎麼回事有什麼想法?

+0

我的猜測是你看到的是你的浮點數的四捨五入,而且這個比例是實際上剛超過1.0。 – mdurant

+0

您是否知道我可以如何擴展我的輸出以查看舍入錯誤,或者我可以如何調整? –

+0

我用你的號碼得到正確的結果。你確定問題在於這些數字嗎?你是否嘗試從這些數字開始手動計算acos?你確定在腳本中有些數字不是整數嗎? –

回答

1

當我運行代碼:

import math 

def foo(x, y): 
    x1, x2, x3 = x 
    y1, y2, y3 = y 
    s1 = math.sqrt(((x2-x1)**2)+((y2-y1)**2)) 
    s2 = math.sqrt(((x3-x2)**2)+((y3-y2)**2)) 
    s3 = math.sqrt(((x3-x1)**2)+((y3-y1)**2)) 
    num1 = (s1**2)+(s2**2)-(s3**2) 
    den1 = (2)*(s1)*(s2) 
    theta1 = math.acos(num1/den1) 
    num2 = (s1**2)+(s3**2)-(s2**2) 
    den2 = (2)*(s1)*(s3) 
    print repr(num2), repr(den2) 
    print repr(num2/den2) 
    theta2 = math.acos(num2/den2) 
    num3 = (s3**2)+(s2**2)-(s1**2) 
    den3 = (2)*(s3)*(s2) 
    theta3 = math.acos(num3/den3) 

foo([0, 4, 1], [0, 4, 1]) 

我拿到num2/den2 == 1.0000000000000004。除非您打印完整精度,否則您可能沒有注意到num2略微大於大於den2這會導致略大於1的值。很明顯,因爲餘弦的最大值是1,那麼你不能把的大小設爲大於

+0

感謝您的幫助。對於將來的任何人,我使用吊頂函數來封閉舍入誤差,並進行檢查以確保它不會將零點歸零。 –