2016-12-20 1 views
0

평면 시스템을 해결하기위한 프로그램을 만들고 비행기가 일치하는지 감지하지 못했습니다. AKA : 배열 A의 요소가 배열 B의 요소의 배수인지 확인해야합니다. 이것은 내가 지금까지 무엇을 가지고 :배열이 다른 배열의 배수인지 확인하십시오


def coincident(one, two): 
    div_ = one[0]/two[0] 

    for v in zip(one[1:], two[1:]): 
    if v[0]/v[1] != div_: 
     return False 
    return np.dot(one, two) != 0

은 2 개 배열, 현재 더 이상 그 4 개 요소를 받아, 그들로부터 첫 번째 요소를 나눕니다. 그런 다음 나머지 요소를 반복하고 배당금이 'div_'와 같은지 확인합니다. 마지막 줄은 배열에 모두 0을 포함하는 것으로, numpy를 사용하여 제품에 점을 찍고 0인지 확인합니다.

이것은 어떤 이유로 작동하지 않으며 제로를 잘 처리하지 못합니다 (0으로 나누기).

+0

초기 목록과 원하는 결과가있는 샘플 예제는 여기에서 도움이 될 것입니다. –

+0

예상 결과와 함께 몇 가지 입력 예를 추가 할 수 있습니까? 'l1 = [1, 2, 3]'과'l2 = [2, 4, 6]'와 같이 함수가'True'를 반환해야한다는 것을 의미합니까? – ettanany

+0

'one = two * 4.5', 즉 'one'의 요소가 'two'의 해당 요소와 '4.5'배 곱한 경우, 출력은 무엇이되어야합니까? – Divakar

답변

2

은 2 ~ 확인 열이 입력 인 2 차원 배열 배열 (나는 1 차원이라고 가정)을 계산하고 행렬 ranknumpy.linalg.matrix_rank을 사용하여 계산합니다. 입력 배열이 일치하면 순위는 1 이하가됩니다.

다음은 몇 가지 예입니다. 첫째, 두 개의 무작위 입력. 순위는이 있어야한다, 그래서 일반적으로 이러한는 일치하지 않습니다 :

In [114]: np.random.seed(12345) 

In [115]: x = np.random.rand(4) 

In [116]: y = np.random.rand(4) 

In [117]: np.linalg.matrix_rank(np.column_stack((x, y))) 
Out[117]: 2 

이제 yx의 배수합니다 예상대로 순위, 1

In [118]: y = x/23 

In [119]: np.linalg.matrix_rank(np.column_stack((x, y))) 
Out[119]: 1 

.이 계정에 일반 부동 소수점 부정확하지 않기 때문에 코드는이를 감지하지 않습니다

참고 :

In [120]: coincident(x, y) 
Out[120]: False 
+0

감사합니다. 부동 소수점 부정확성을 알아 차 렸습니다. – Memcallen

5

당신이 정말로 다음 정확한 여러 필요한 경우 :이 작동

def coincident(one, two): 
    return np.dot(one,two)*np.dot(one,two) == np.dot(one,one)*np.dot(two,two) 

을하기 때문에 A⋅B = | t이 사이의 각도입니다 * COS (t), | A | * | B 두 벡터, 그래서 (A⋅B) ² = | A | ² * | B | ² * cos² (t). 벡터가 서로 배수이면 t는 0 또는 180도이고 cos² (t) == 1입니다.

부동 소수점 숫자로 작업하는 경우 약간의 반올림 오류를 허용해야합니다. 당신이 벡터는 예를 들어, 0.01도 이내에 동일 선상되고 싶어요, 당신은 그들 중 하나가 0 인 경우를 제외하고 싶은 경우에, 당신은 할 수 있습니다 :

def coincident(one, two): 
    abab = np.dot(one,two)*np.dot(one,two) 
    aabb = np.dot(one,one)*np.dot(two,two) 
    return abab > aabb*0.99999997 
0

나는이 모든 경우를 처리합니다 생각합니다.

def coincident(l1, l2): 
    try : 
     d = l2[0]/l1[0] 
    except ZeroDivisionError as e: 
     d = 0 
    if [x*d for x in l1] == l2: 
     return True 
    return False 


l1 = [1,2,3] 
l2 = [3,6,9] 
print(coincident(l1, l2)) 

l1 = [0,6,9] 
print(coincident(l1, l2)) 

출력 : 약간의 수정으로

True 
False 
1

다음과 같이 0으로 나누기를 방지 할 수 있습니다

def coincident(one, two): 
    div_ = one[0]/two[0] if two[0] else 1 

    for v in zip(one[1:], two[1:]): 
    if v[0] != div_ * v[1]: 
     return False 
    return True 

테스트 :

print(coincident([1.1,2.2,3.3],[2.2,4.4,6.6])) # True 
print(coincident([0,0,0],[0,0,0])) # True 
print(coincident([0,0,0],[0,1,0])) # False 
print(coincident([1,-2,3],[2,4,6])) # False 
0

가 원래의 코드에 가까운 체재 및 PT 번호를 떠를 차지, 여기에 한 가지 방법입니다 -

def coincident(a, b): 
    M = a/b.astype(float) 
    return np.allclose(np.round(M),M) & np.allclose(np.diff(M),0) 

우리는 원래 코드에서와 같이 첫 번째 배열을 두 번째 배열로 나누고 나누기 결과가 반올림 된 배열 버전과 비교하여 정수에 가까운 지 확인합니다.

또한 결과가 서로 다른 모든 요소에서 나누기 결과가 동일하고 모두가 0에 가까운 지 확인합니다.

샘플 실행 -

In [318]: b = np.random.rand(4) 

In [319]: a = b*4.0 

In [320]: coincident(a, b) 
Out[320]: True 

In [321]: a = b*4.5 

In [322]: coincident(a, b) 
Out[322]: False 

In [323]: a = b*np.array([3,2,5,6]) 

In [325]: coincident(a, b) 
Out[325]: False 

In [326]: a = b*4.0 

In [327]: coincident(a, b) 
Out[327]: True 

In [328]: a[1] = 100.0 

In [329]: coincident(a, b) 
Out[329]: False 

다양성은 정수 나하지 수, 즉 당신은, 정수 여부 될 수있는 배당에 대해 걱정하지 않는 경우

, 우리는 차별화 부분 만 고려할 것 -

def coincident_ignore_exact_divisibilty(a, b): 
    return np.allclose(np.diff(a/b.astype(float)),0) 
관련 문제