Why do dynamic languages make it more difficult to maintain large codebases?
(programmers.stackexchange.com)(Replying to PARENT post)
I'm not totally convinced, though. Take the simple case of "tell me what range of values to expect here". Java / C++ deal with this with their types, and you can be reasonably confident that you're getting the object you expect. As I'm sure somebody will mention, those types are a bit weak, and can't guarantee the object you get is exactly what you expect. What if you don't test with the right sub-class? What if it's an int, but it's out of the range you expect?
"No, that's not what types guarantee!" you may say. And it's true.
I think one of the problems is that language features aren't perfect. Forcing everybody to admit they're dealing with integers is more desirable than no contract at all, but would it be better if you dealt with Scores, which where integers in the range of 0-100?
In a big enough codebase, the language is never powerful enough to handle all your checking for you, so you need some level of discipline. I worry that by having something "good enough" when your code base is moderate, it allows teams to slip by into "large" without ever considering what their tools, conventions, and limitations should be.
(Replying to PARENT post)
Consider this common mistake:
interface Greet {
void sayHello(String firstName, String lastName)
}
class PrintGreeter implements Greet {
public void sayHello(String lastName, String firstName) {
...
}
}
Where's your compiler NOW?(Replying to PARENT post)
(Replying to PARENT post)
(Replying to PARENT post)
I would say that the most stable codebase would be a static one with lots of tests, but I would also guess that this would be the slowest to develop, and would be the most difficult to implement in a real world team of developers.
I know most of us would balk at a huge codebase with zero tests, but it happens all the time. I would definitely prefer a dynamic code base in which I could get my team to write decent tests, but give up type safety, than to have type safety at the cost of decent tests.
(Replying to PARENT post)
I only see one link to that answer on SO that points to a single study. It was provided by another commentator asking for the OP to provide evidence for the "strong correlation," claim. Not very good.
Though I'd hate to work with a team that used a statically typed language and tools that didn't write tests for their software. It's not magic soya-sauce that frees you from ever introducing bugs into your software. Most static analyzers I've seen for C-like languages involve computing the fixed-point from a graph (ie: looking for convergence). Generics makes things a little trickier. Tests are as much about specification as they are about correctness.
In my experience there are some things you will only ever know at run-time and the trade-off in flexibility for static analysis is not very beneficial in most cases.
Some interesting areas in program analysis are, imho, the intersection of logic programming, decomposition methods and constraint programming as applied to whole-program analysis. Projects like kibit in Clojure-land are neat and it would be cool to see them applied more generally to other problems such as, "correctness," and the like.
(Replying to PARENT post)
"Rather it is also everything else [correctness facilities besides static typing] that is frequently missing from a dynamic language that increases costs in a large codebase. Dynamic languages which also include facilities for good testing, for modularization, reuse, encapsulation, and so on, can indeed decrease costs when programming in the large, but many frequently-used dynamic languages do not have these facilities built in. Someone has to build them, and that adds cost."
...I think that's a little generous to statically typed languages. C and C++, both heavy-hitters in the static language world, have anemic modularization, reuse, encapsulation, mocking frameworks, etc.
(Replying to PARENT post)
(Replying to PARENT post)
A language with strong typing facilitates communication about the intent of code as well as its function. Strong typing is easier to build into a static compilation phase, but this is not an absolute requirement.
Granted, three of the four quadrants are well covered. Dynamic, strongly-typed languages will take a speed hit unless designed by a wizard.
(Replying to PARENT post)
(Replying to PARENT post)
Sounds great on paper, I know, and is much harder in practice. But if done correctly then dynamic languages are awesome boosts to productivity.
(Replying to PARENT post)
So I don't know if I have an answer to this question -but certainly it appears, to me, that the more dynamic the language is - the easier it is to maintain .. certainly the mere fact of lighter tooling means this is true?
(Replying to PARENT post)
(Replying to PARENT post)
(Replying to PARENT post)
(Replying to PARENT post)
Object.class_eval do
def to_s
"a"
end
end
# in some other context perhaps a controller action... def lookup_user
user = User.find_by_name(params[:name].to_s)
if user.blank?
flash[:error] = "No user found by that name"
redirect_to "/users"
return
end
# good stuff goes here
end
#
# try debugging it... it's tricky... use grep?
#the thing is this is actually not too bad... in C++ try debugging a memory leak...
(formatting...)
(Replying to PARENT post)
(Replying to PARENT post)
Statically typed languages should just provides code that need to be reused often. Also needed when you need performance or low power consumption.
Scripting should be about using those libraries together.
People should try to understand how gmail works, because I think javascript is just used for presenting data to a browser, while gmail servers do the heavilifting.
(Replying to PARENT post)
(Replying to PARENT post)
Static types are not enough to ensure that your algorithm receives correct input, to ensure you that you will need to write tests anyway. So with static languages you get one check "for free" out of the many that you will have to write yourself.
If you rigorously write tests for a JavaScript code as you would have for a Java code, it becomes just as reliable.
(Replying to PARENT post)
Remember, great software can be made with any programming language! This is why all your favorite apps are written in Visual Basic. Hope this helps!
(Replying to PARENT post)
I ask this because it seems like a lot of "big code" issues stem from poor development practices polluting the codebase over a long period of time, destroying any sort of design that once existed.
Does it help if the language takes a hardline stance against mutable state and side effects? I'm certain you can screw those up, but it's confined to a single place.
(Replying to PARENT post)
Maybe the idea that you can avoid side effects is a fiction that the horror of manual memory management cures you of.
(Replying to PARENT post)
(Replying to PARENT post)
And you really, really should try harder to make small isolated components (services, daemons, sites, commands, whatever) and avoid large codebases.
(Replying to PARENT post)
(Replying to PARENT post)
(Replying to PARENT post)
(Replying to PARENT post)
(Replying to PARENT post)
(Replying to PARENT post)
(Replying to PARENT post)
(Replying to PARENT post)
If you're using Java or C++ or mainstream OOP, you're not getting the benefits out of static typing anyway and a Python or Clojure is a big improvement. That said, there are domains where compile-time static typing is extremely useful (and justifies the associated costs due to, e.g., the loss of a Lisp's intuitive macro system and first-class REPL) but those are going to call for a Hindley-Milner type system, not Java's weird mess of one.
(Replying to PARENT post)
Please note (if you can't be bothered to read the actual post before responding), I am _not_ saying that static typing has no value. I'm saying it has both a value _and_ a cost, and too many arguments seem to consider only one of these.