Common Lisp type declarations not working as expected

北战南征 提交于 2019-12-10 13:56:20

问题


When I define a function in Common Lisp like this:

(defun foo (n)
  (declare (type fixnum n))
  (+ n 42))

I expected a call like (foo "a") to fail right away but it instead fail at the call to +. Is the declare form not guarantees static type checking?


回答1:


Type declarations are traditionally meant to be used as guarantees to the compiler for optimization purposes. For type checking, use check-type (but note that it, too, does the checking at run-time, not at compile-time):

(defun foo (n)
  (check-type n fixnum)
  (+ n 42))

That said, different Common Lisp implementations interpret type declarations differently. SBCL, for example, will treat them as types to be checked if the safety policy setting is high enough.

In addition, if you want static checking, SBCL is probably your best bet as well, since its type inference engine warns you about any inconsistencies it encounters. To that end, ftype declarations can be put to good use:

CL-USER(1): (declaim (ftype (function (string) string) bar))

CL-USER(2): (defun foo (n)
              (declare (type fixnum n))
              (bar n))
; in: DEFUN FOO
;     (BAR N)
; 
; caught WARNING:
;   Derived type of N is
;     (VALUES FIXNUM &OPTIONAL),
;   conflicting with its asserted type
;     STRING.
;   See also:
;     The SBCL Manual, Node "Handling of Types"
; 
; compilation unit finished
;   caught 1 WARNING condition

FOO



回答2:


Declarations are just hints to the compiler so it can produce more efficient code. In other words, it is not static checking.



来源:https://stackoverflow.com/questions/9521593/common-lisp-type-declarations-not-working-as-expected

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!