2012-04-02 2 views

답변

11

예, 상한선이 있지만 정확한 상한선은 구현에 따라 다릅니다. 최소한 50 세 이상은 통과 할 수 있지만 모두 달라질 수 있습니다. 목록을 합산해야하는 경우 (reduce #'+ list)을 사용하는 것이 더 나을 것입니다. 다른 방법보다 훨씬 뛰어난 확장 성을 제공해야합니다.

Common Lisp HyperSpec에 대한 정보가 더 있습니다.

값 범위에 관해서는 두 가지 경우 인 부동 소수점과 정수가 있습니다. 수레는 크기에 따라 본질적으로 제한을받으며 한 수레에서 두 수레로 변경된 구현은 나를 많이 놀라게 할 것입니다. 정수 및 합계를 사용하면 CL은 fixnum과 bignum 사이를 완벽하게 전환하므로 제한은 구현에 사용할 수있는 사용 가능한 주소 공간의 함수입니다. 복합 번호 (복잡한 정수 및 합계 - 필요한 경우 bignum으로 이동, 복잡한 수레 -> 범위를 벗어나거나 Inf 또는 NaN을 반환 함)에 대해 동일하게 적용됩니다.

+0

그게 스펙이 말하는 것입니다.하지만 실제로 한도를 시행하는 구현에 대해 알고 있습니까? – Marcin

+2

@Marcin 글쎄, SBCL은 10^18의 지역에서 콜 리퀘스트 제한을 보장합니다. 저는 다른 구현 방법을 손쉽게 잡을 수는 없지만, "수백 가지 요소"와 같이 짧은 목록으로 줄이기 대신 APPLY를 사용하는 사람들에 대해 읽은 것을 기억합니다. – Vatine

+1

@Vatine 방금 제목과 질문 내용이 의도 한 의미에서 서로 모순된다는 것을 알았습니다. 나는 당신이 "+"함수의 값 한계에 응답하고 있다고 생각하기 때문에, 함수가 가질 수있는 _inputs_의 한계에 대해 언급하고 싶습니까? 혼란을 드려 죄송합니다! – Soyuz

-1

간단한 대답, 아니, 재귀가 아니라 꼬리 재귀를 사용하여 가난한 구현 스택 제한이있을 것이다 있지만.

구현에 따라 재귀를 사용하거나 직선 함수 호출로 구현할 수 있습니다.

커스텀 리스프가 어떤 요구 사항을 규정하는지 충분히 알지 못하지만 대부분의 구현에서는 재귀를 사용하는 경우 꼬리 재귀를 사용하고 스택 제한을 피할 것입니다.

함수 호출은 인수를 목록으로 액세스 할 수 있으므로 처리 할 수있는 인수의 수에는 제한이 없습니다.

EDIT : 실제로 누군가가 Common Lisp 참조를 제공 했으므로 분명한 답이 분명히 있어야하지만 충분한 인수가 제공 될 때 어떤 좋은 구현이라도 자동으로 (reduce #'+ arg-list)을 적용 할 것이라고 생각했을 것입니다.

+0

일반적인 Lisps는 일반적으로 꼬리 재귀가 아닙니다. 내가 꼬리 호출 최적화를 허용하지 않는 이유가 있음을 읽은 느낌이 들지만 (물론 그렇게 상상할 수도 있음). – Marcin

+1

또한,'reduce'와'loop'의 가용성을 고려할 때 구현이 재귀를 사용할 이유가 없습니다. – Marcin

+2

@Marcin 최적화 변수를 꼬집어서 (주로 "속도가 빠름"과 "디버그"가 낮지 만 구체적인 것은 구현 매뉴얼 참조) 꼬리 호출 최적화가 가능합니다. – Vatine

8

Common Lisp은 다양한 하드웨어 및 소프트웨어 시스템에서 효율적으로 구현 될 수있는 방식으로 정의되었습니다. 예로 Motorola 68000/20/30/40, 다양한 Intel x86 프로세서, Lisp Machine 스택 기반 프로세서, DEC VAX, RISC 프로세서, Cray의 슈퍼 컴퓨터 등이 있습니다. 80 년대에는 Lisp 코드를 실행하기 위해 개발 된 프로세서를 포함하여 많은 프로세서 제품군이 경쟁했습니다. 오늘날 우리는 여전히 여러 프로세서 제품군 (x86, x86-64, ARM, SPARC, POWER, PowerPC 등)을 보유하고 있습니다.

C, Scheme 또는 다른 프로그래밍 언어로 컴파일 할 수도 있습니다.

또한 CMUCL, CLISP 또는 JVM/Java 가상 머신과 같은 가상 시스템으로 컴파일 할 수 있습니다 (Java 가상 머신에는 인수가 254 개로 제한되는 것 같습니다).

예를 들어 Common Lisp 컴파일러는 Lisp 코드를 컴파일하여 C 코드를 컴파일 할 수 있습니다. 따라서 C 컴파일러의 함수 호출이 최대한 많이 재사용 될 수 있다면 좋을 것입니다. 특히 C에서 Lisp를 쉽게 호출 할 수 있습니다.

는 C/C++도, 그 제한을 갖는다 :

Maximum number of parameters in function declaration

위의 C 127 (C)와 같은 번호 256 ++ 준다. Lisp에서 C 컴파일러에 이르기까지 이것은 한계 일 수 있습니다. 그렇지 않으면 Lisp 코드는 C 함수 호출을 사용하지 않는다. 최초의 컴파일러 KCL (교토 커먼 리스프는 나중에이 구현은 GCL/GNU 커먼 리스프와 ECL/포함 가능한 커먼 리스프로 진화)

는 LispWorks/맥 OS X의 CALL-ARGUMENTS-LIMIT

(64)의 64 비트 구현했다 예를 들어, CALL-ARGUMENTS-LIMIT에 대해 2047의 값을가집니다.

CALL-ARGUMENTS-LIMIT

는 호출 인수가 관련되지 않는다 (50)보다 더 작은 CL의 목록 처리에 따라서

되어야한다. 목록을 처리하려면 목록 처리 도구 (LIST, MAPCAR, APPEND, REDUCE, ...)를 사용해야합니다. Common Lisp는 &REST 매개 변수를 사용하여 인수를 목록으로 액세스하는 메커니즘을 제공합니다. 그러나 인수의 목록이 필요하므로 함수 호출 오버 헤드를 유발할 수 있으므로 일반적으로이를 피해야합니다.

2

Clojure의 게으른 시퀀스의 사용을 통해, 당신은 실제로 함수 인수의 무한한 수를 가질 수 리스프의 예를 제공합니다

; infinite lazy sequence of natural numbers 
(def naturals (iterate inc 1)) 

(take 10 naturals) 
=> (1 2 3 4 5 6 7 8 9 10) 

; add up all the natural numbers 
(apply + naturals) 
=> ...... [doesn't terminate] 

특히 유용하지 않음을 물론 .....

+0

이 예는 나를 설득하지 않습니다. APPLY는 두 개의 인수로 호출됩니다. 무한한 논쟁으로 호출되는 것은 명확하지 않습니다. 어쩌면 APPLY가 BEFORE +가 무한 인수로 호출되는 중일 수 있습니다. @jwinandy가 Clojure가 8192 개의 인수로 '정지'한 것을 보여주는 예가 주어지면 여기에서도 같은 결과가 발생할 것이라고 생각됩니다. –

2

구현에 따라 다릅니다. "LISP 사용자가 플랫폼 테스트에 5 분이 걸릴 것을 제안합니다." Clojure의

(defn find-max-n [n] 
    (try 
    (eval (concat (list +) (take n (repeat 1)))) 
    (println "more than" n) 
    ; return n if something goes wrong 
    (catch Exception e n)) 
    (recur (* n 2))) 


(find-max-n 1) 

그것은 종료되지 않습니다 들어

, 그것은 내 설정 주어진 8192에서 멈 춥니 다.

more than 1 
more than 2 
more than 4 
more than 8 
more than 16 
more than 32 
more than 64 
more than 128 
more than 256 
more than 512 
more than 1024 
more than 2048 
more than 4096 
more than 8192 
관련 문제