By contrast to other answers, there are cases where returning different types is acceptable.
Example 1
sum(2, 3) → int
sum(2.1, 3.7) → float
In some statically typed languages, this involves overloads, so we can consider that there several methods, each one returning the predefined, fixed type. In dynamic languages, this may be the same function, implemented as:
var sum = function (a, b) {
return a + b;
};
Same function, different types of return value.
Example 2
Imagine you get a response from an OpenID/OAuth component. Some OpenID/OAuth providers may contain more information, such as the age of the person.
var user = authProvider.findCurrent();
// user is now:
// {
// provider: 'Facebook',
// name: {
// firstName: 'Hello',
// secondName: 'World',
// },
// email: 'hello.world@example.com',
// age: 27
// }
Others would have the minimum, would it be an email address or the pseudonym.
var user = authProvider.findCurrent();
// user is now:
// {
// provider: 'Google',
// email: 'hello.world@example.com'
// }
Again, same function, different results.
Here, the benefit of returning different types is especially important in a context where you don't care about types and interfaces, but what objects actually contain. For example, let's imagine a website contains mature language. Then the findCurrent()
may be used like this:
var user = authProvider.findCurrent();
if (user.age || 0 >= 16) {
// The person can stand mature language.
allowShowingContent();
} else if (user.age) {
// OpenID/OAuth gave the age, but the person appears too young to see the content.
showParentalAdvisoryRequestedMessage();
} else {
// OpenID/OAuth won't tell the age of the person. Ask the user himself.
askForAge();
}
Refactoring this into code where every provider will have its own function which will return a well-defined, fixed type would not only degrade the code base and cause code duplication, but also will not bring any benefit. One may end up doing horrors like:
var age;
if (['Facebook', 'Yahoo', 'Blogger', 'LiveJournal'].contains(user.provider)) {
age = user.age;
}
The main benefit of a DI framework is that it moves construction into a different language (xml, json, whatever). This enforces not mixing construction code with behavior code. It's a poor programming team that needs that, but it works.
DI doesn't require a framework. Simply not mixing these responsibilities is enough. Construction also doesn't have to be done procedurally in main. You're entitled to use every feature of the language. Creational patterns have come a long way. It's when you mix use and construction that you find yourself hard coding dependencies with no way to override.
Good defaults are extremely easy to override as needed in a language with named parameters. This makes a much bigger impact to DI then dynamic typing. DI works well in dynamic languages. Even prototypical languages can benefit. That's because DI's is more then just mechanical. It actually makes code easier to read, if you're doing it right.
I recommend everyone learn how to do DI without a framework before trying to evaluate what any one framework provides. Some are useful even when you have the skill to live without them. Some are just something else trying to convince you to become dependent on it. Use with caution.
Best Answer
Yes, definitely.
Dynamic typing has definite advantages in cases where you want to be able to treat everything as one single type. Serialization/deserialization is one of the classic examples. This is why so much Web programming is done in dynamically-typed scripting languages: they're well-suited to a task which involves a whole lot of converting all sorts of data to and from strings.
For application programming, on the other hand, static languages work much better because trying to treat everything as one single type is not frequently a requirement. You often want to have efficient data structures with data represented as itself and not getting converted to other types very frequently. This makes the features of dynamic typing a drawback instead of a benefit, which is why applications are almost exclusively written in statically typed languages.