8 ms·
Having a compiler that will tell you all the places that you need to change things is an amazing productivity booster. Agree with this 100%. I think dynamicall
by cageface 15y ago
Having a compiler that will tell you all the places that you need to change things is an amazing productivity booster.
Agree with this 100%. I think dynamically typed languages are a transitional technology we'll mostly leave behind as the kinks get worked out of modern type systems.
- grey-area 15y agoIt would have been interesting (and perhaps a little more convincing) to see some examples of the Haskell type system boosting productivity in such a dramatic way. I can count on one hand the number of type issues which have caused trouble for me in Ruby over > 5 years of producing complex systems with it. I haven't used Haskell though so would be interested to see some examples of this. If his audience is Ruby users, it is not very informative to just say it is better in a general way. The main point of comparison in the article point 1 seems to be with unit tests, however there are no concrete examples given of a failing test from a real program where types would have helped. A strong type system adds friction and verbosity, so it would need to come with a lot of advantages for me to prefer it to Ruby, which will not allow something like 2 + "2" but does try to get out of your way as much as possible. It's quite hard to compare type systems as they vary so much but at least here is he comparing just two systems Ruby/Haskell, so comparisons can be straightforward examples of situations where types have caused him trouble with direct comparisons. I'd be interested to see an example of something like a telephone number (from untrusted user input) where the Haskell type system is superior to having some checks on formatting, and an explanation for those less familiar with Haskell of what advantages the type system gives.
- cageface 15y agoI worked almost exclusively in Ruby and Python over the last ten years and coming back to static languages after that long was a real eye-opener. A good type system doesn't just help you catch a certain class of bugs. It completely changes the way you write code. Functions become self-documenting, aggressive refactoring becomes routine, the underlying architecture of your code emerges much more clearly. And you usually get much faster code for free. It's like having a genius savant pair partner. In my experience a good type system doesn't add much friction and the extra documentation you get from specifying types more than pays for itself in the long run.
- pjmlp 15y agoI used to like dynamic languages. Nowadays I will take a static language with automatic type inference over a dynamic language anytime, preferably one that with direct support for FP. The IDE support, code navigation and refactoring, and runtime performance just beat dynamic languages all the time. For the few use cases where dynamic types really make a difference, that can be supported by some kind of variant type or reflection.
- djhworld 15y agoHaskell isn't quite there in terms of IDE support (there is "Leksah") but I find myself writing most Haskelly code in emacs/vim with GHCI open in a separate terminal.
- pjmlp 15y agoI just make use of EclipseFP, it is a very comfortable IDE for Haskell. http://eclipsefp.github.com/ http://eclipsefp.github.com/
- sanderjd 15y agoI'm at this point right now - what are the best static languages with type inference for the dynamic language crowd? Haskell? Scala? Go? Rust? Something I haven't heard of? All of the above?
- dagw 15y agoPretty much same experience here. I'm currently working a pretty large and fairly old Python code base. And while I'd still consider python my favorite language, I no longer really feel comfortable recommending it (or any other equally dynamic language) for large, long lived, projects that's worked on by several developers. Sure, all problems can be solved in theory with things like meticulous documentation, rigorous coding standards that everybody follows and lots of detailed tests. But in practice those sort of informal constraints will break down over years as developers of varying skill levels come and go. Better to formally force as much of that as possible with a decent type system.
- chc 15y agoThe thing is, it's not that straightforward. It's not about avoiding type errors that would have cropped up in Ruby, but about getting the type system to encode as much of your program's semantics as possible. For example, in Ruby, you use strings and symbols for a lot of disparate things. In Haskell, you'd introduce a type for each purpose to encode your intent in a way the compiler understands†. In Haskell, you're actually going out of your way to create more potential type errors, because that's more stuff the compiler can check for you. † Concrete example off the top of my head: In Ruby, we do `foo.instance_variable_get(:@bar)`. If we accidentally write `foo.instance_variable_get(:bar)`, that's a hard error, but it isn't a type error. Haskellers would generally express a constraint like that with the type system, so the compiler would let them know when they made such a mistake. (Also, don't forget that every unintended nil is a type error! If you've been doing heavy Ruby work for years and gotten fewer than six NoMethodErrors, I will hang my head in shame.)
- mtrimpe 15y agoI agree very much. As far as I'm concerned Java's biggest failure, orders of magnitude worse than all others, is to make java.lang.String a final class.
- masklinn 15y agoI don't know: 1. having nullable references by default strikes me as a bigger issue 2. I don't see any reason I'd want to subclass String, actually (though I could see wanting to create an alternate implementation e.g. ropes-based). So String being a final class makes perfect sense as far as I'm concerned (unless it were an interface or some sort of "proxy" class as is often done in Cocoa). On the other hand, I'd give a phalange to easily create an unrelated type (typesystem-wise) with the same implementation. What `newtype` provides in Haskell.
- riffraff 15y agohow would a nominally different string type be better than wrapping the string ? I mean I understand why having a Name, ZipCode or UUID stringish class helps ensure program correctness, I do not understand (out of ignorance) how it would improve your code vs a wrapper.
- maxcan 15y agoI can't count on one hand the number of commits with >500 changes that did not introduce a single bug or regression due to the compiler catching a huge amount of little typoes and mistakes that would have slid by in a dynamic language. Its like how most vehicle accidents involving impact speeds of over 300 MPH involve planes and not cars or boats. Its not that cars and boats are safer..
- pjmlp 15y agoThat is the biggest problem with dynamic languages, they don't scale. In the enterprise projects where I work, usually with around 200+ developers scattered around the globe, it is unthinkable to use dynamic languages in such environments. We already have issues with static languages in the CI system. I cannot think how it would look like doing the project in a dynamic language.
- grey-area 15y agoFair enough - I accept dynamic languages are not always suited to larger projects, particularly with a large number of developers involved all working on the same code. I suppose it is possible to impose structure in a dynamic language by having strict rules about interfaces and documentation, but at some point (which you have obviously experienced) it becomes much more attractive to have the compiler do it for you. For smaller projects however, with smaller teams, dynamic languages do have less overhead, which is perhaps why they are so popular for web apps.
- gnuvince 15y agoAs other commenters have said, in statically typed languages you try and design your program so that more errors are caught at compile time. As an example, watch Yaron Minsky's "Effective ML" talk. He shows how he takes a data structure and modifies it to make illegal states (such as having a disconnection time while being connected) type errors. With a language with Ruby, you couldn't do something like that, so you'd classify the error of having a disconnection time while being connected as a semantic error or a human error. With the proper tools, you can make it a type error.
- masklinn 15y ago> Agree with this 100%. I think dynamically typed languages are a transitional technology 54 years old transitional technologies? Look the split between dynamic typing and static typing is as old as computing itself (older actually, see untyped v typed lambda calculi), as it looks to me you're asserting properties your prover can't cash.
- cageface 15y agoDynamic languages are easy to implement. Type systems that are rigorous enough to be useful but flexible enough to be expressive are much, much harder to design. I think we're still not quite there yet but we've made a lot of progress in the last decade. Even after ten years of Ruby experience I find myself writing code in Scala that has fewer bugs and is vastly easier to understand and maintain. Maybe my background in chemistry colors my view but I don't see 54 years as really such a long time for any intellectual discipline. We're still in the early days of software engineering, IMO.
- sethg 15y agoI think dynamic and static type systems will eventually meet somewhere in the middle. Haskell has a “Dynamic” type for those times when you really do want to include dynamic types in your program. And some researchers have experimented with “soft typing” systems for dynamic languages like Scheme and Python, where a type analyzer tries to infer the types of expressions from how they are used.
- dustingetz 15y agosee "Horrors of Static Typing"[1] the thesis is that there are places where the type system just gets in the way, and there are places where it is invaluable. [1] http://phillyemergingtech.com/2012/system/presentations/Horrors_of_Static_Typing.pdf http://phillyemergingtech.com/2012/system/presentations/Horr...
- SkyMarshal 15y ago>Agree with this 100%. I think dynamically typed languages are a transitional technology we'll mostly leave behind as the kinks get worked out of modern type systems. While my favorite language right now is Haskell due to its sophisticated type system and ambitious design goal of enabling engineers to coral and isolate error-causing code into monads, I have to disagree. Dynamic languages can be looked at as the next evolution of non-memory-managed -> memory-managed. Next is statically/strongly typed -> dynamically-typed. In both cases you go from manual management of some feature of the language, to having the vm or compiler do it for you, and that increasing abstraction and automation is the story of language development (and technology in general). Non-memory-managed languages like C, C++, ObjC are still around and are used by highly skilled developers to squeeze the utmost performance out of the system, Chromium/Chrome/V8 being a good everyday example. But where that kind of optimization is not strictly needed or where the automatic memory management of, say the Hotspot JVM, is sufficient, memory-managed languages will flourish. Further, memory-managed languages benefit from the continuous improvement in vm technology, and over time continue to approach non-managed in many situations. I expect something similar to happen with type systems. Where a particular project does not need the strict control provided by a type system, dynamically typed languages will flourish (as they are in the startup web space). Perhaps one day, vm's and dynamic type inference will be so good that neither manual memory-managed languages nor strongly typed ones will be necessary,but given Haskell's design goals and the type of difficult problems it's trying to solve (software assurance, security, etc.) I don't expect that will be anytime soon. They'll all continue to coexist for the foreseeable future. Having said that, Haskell's type system is a pleasure to use, and imho actually increases productivity by both requiring and helping you think more clearly about the data flowing through your code.
- lincolnq 15y agoWow, interesting perspective. Let me attempt to summarize what you said: When compilers/runtimes become smart enough, you won't need a static type system, because the runtime one will catch all your errors. Here's why I think it's wrong: Catching errors is not something that I want done at runtime.
- 15y ago