2017-10-30 5 views
2

을 나는 재발을 이해 생각했지만, 다음과 같은 사용은 이해가되지 않습니다 :여기에 반복되는 방식은 무엇입니까? [Clojure의]

(fn gcd [a b] 
    (if (= b 0) 
     a 
     (recur b (rem a b)))) 

기능은 두 수의 최대 공약수를 검색합니다. 4와 2의 경우 함수는 2를 반환합니다.

recur가 함수에 바인딩 될 수 있다는 것을 알고 있지만 'b'는 변경없이 반복됩니다. 일반적으로 루프의 값을 변경하려면 a (inc b)와 같은 것을 넣어야합니다.

무엇이 누락 되었습니까?

답변

3

여기서 gcd 함수는 Euclidean algorithm을 사용하여 두 개의 숫자로 이루어진 가장 큰 공약수를 찾습니다.

인수 목록에 이 포함되어 있지만이 함수는 b, (rem a b)에 대해 호출되므로 함수가 작동하고 종료됩니다. 여기 b의 장소가 변경됩니다 (seond 장소에서 first place까지).

값이 b이 할당되었으므로 a의 값이 변경되었습니다. 또한 b의 값은 (rem a b)이 할당되어 (따라서 감소 함) 변경되었습니다. 따라서 호출이 반복 될 때 두 값이 모두 감소하고 결국 호출 중 하나가 0이되면 (재귀가 중지됩니다).

2
(fn gcd [a b] 
    (if (= b 0) a 
    (recur b (rem a b)))) 

는 예를 들어 I는 인수 A = 24, B = 16 B가 제로가 아니기 때문에이 함수만큼 재귀 호출하여이 함수를 호출한다.

(gcd 24 16) 
=> (gcd 16 8)) #_"because b=24 doesn't equal to zero and 8 is the reminder of 24/16" 
=> (gcd 8 0) #_"0 is the reminder of 16/8" 
=> 8 

이 계산은 b가 0에 도달했기 때문에 중지됩니다.

2

예 재귀 호출에서 값을 변경하려고하므로 결국 테스트가 성공하고 재귀가 중단됩니다. 이 알고리즘은 이전의 second 매개 변수의 값으로 새로운 first 매개 변수를 전송함으로써 정확하게 수행하고, 새로운 두 번째 매개 변수는 이전의 첫 번째 및 이전 두 번째 매개 변수를 기반으로 재 계산됩니다.

함수에서 if 문 앞에 (println "a:" a "b:" b)과 같은 것을 추가하면 답을 찾는 동안 순환하는 값이 표시됩니다.