It could be you heard an extrapolation of Postel's law: "Be conservative in what you send, liberal in what you accept."
Mostly it's about maximizing code reusability. It's easy to come up with cases to demonstrate why it helps. Consider Java's
Iterable<T> as an example. If the only thing your method does is iterate through all the
Ts, having an
Iterable<T> as your parameter type allows you to use that method with over 60 built-in classes, not to mention any custom classes that implement the interface. If you limited it to, say,
Vector<T>, then any code that calls your method would have to convert to a
On the other hand, returning an
Iterable<T> from a method limits the amount of code that can use your return value to those that take an
Iterable<T> parameter. If you return a very concrete type, like
Vector<T>, then your return value can be passed into any method that takes a
AbstractCollection<T>, and it will work as expected.