4 ms·
The way I approach it is to make use of the Design By Contract features Clojure took from Eiffel. I almost never want to restrict an input to a function to a sp
by retrogradeorbit 11y ago
The way I approach it is to make use of the Design By Contract features Clojure took from Eiffel. I almost never want to restrict an input to a function to a specific type or interface. I want it to conform to some kind of contract. So you build the :pre clause to reflect what kind of input you want. Sometimes I add a :post clause to ensure the function has performed correctly.
What does annoy me though (and you can see it clearly reflected in the survey respondents putting such a weight on better error messages) is the way assertions don't give me a traceback (or file name and line number of the assertion).
http://blog.fogus.me/2009/12/21/clojures-pre-and-post/ http://blog.fogus.me/2009/12/21/clojures-pre-and-post/
- hellofunk 11y agoRuntime assertions (like the :pre clause) are the only way to really do this in a dynamic language, but they are merely a band-aid, and suffer these problems: 1) You have to actually write the assertion/:pre all the time, which is not a trivial step in my opinion. A basic type system just removes this chore altogether. Writing these little assertions really breaks the wonderful flow of elegance. 2) Any errors are only caught with a specific input that would violate the assertion; some inputs might pass, and others not. Therefore, you may not know there is a possible bug that will crash your app or lead to unexpected behavior, even if it runs fine for a long time. 3) You have to keep flipping the assertions switch on and off as you move from testing to deployment, or, just leave them on and suffer the runtime overhead of their checking everything all the time. 4) You will typically write more unit tests to make-up for the tests a type system does for you.