I'm not speaking to whether dynamic/duck typing is good or bad here, just pointing out that the question is flawed.
Java's reflection system exists to answer this question. I'm not a Java guru though, so i couldnt forumlate the equivalent code
(I say "sort of" because even in Python this is a weird thing; the traditional answer to the question "can I call this as a function" is to simply try it and catch the exception if it fails.)
This isn't true. Here's a trivial scenario for you: a user inputs a URL which represents a web service and a method name. Your code needs to determine if the object which will get returned as JSON by that web service implements the method or not.
There are more complicated examples which occur in actual production systems. For example, suppose you're interfacing with Big Freaking Enterprise code that you can't change, and there is a rule that certain objects have to have certain checks done prior to being sent over the wire. Those checks might be implemented as methods decorated with @FireThisCheckBeforeSendingThisOverTheWire annotations, but that isn't the only way to skin this particular cat. In particular, your million lines of legacy code might have a coding convention where any method starting with "check" gets fired. This worked fine when the code was only running in its own little world and teams of overpaid engineers maintained lists of all the check methods for various classes, but now that code needs to get exposed via a new API to meet some emergent business need, and you want to accomplish this without touching the million line codebase that nobody really understands. Enter the reflection API.
Incidentally, expecting a coding convention like that to actually work isn't totally insane. JUnit 3, I think, treated any method starting with test as a test. I personally prefer it for usability over "slap an annotation on it".
Anyhow, Enterprise Java: abandon all hope ye who enter here.
You wouldn't do that by reflection, you'd have a mapping between service method names and objects that perform the service. In fact, this sort of thing is pretty typical in web frameworks based on dynamic languages as well. I don't want you calling Object.notifyAll or whatever just by fiddling with urls. Reflection does come up but it's usually in more magical places - serialization (the built-in serialization is an example of interface-by-convention), profilers, debuggers, prototyping tools.
Animal animal = zoo.getAnimal();
Can I do animal.bark() or animal.fly() ? All I know is that it's an Animal of some sort, may or may not be an instance of the Dog or Bird subclasses of Animal.
Unless the Animal type responds to fly and bark (unlikely in this scenario) that looks like a compile error to me.
def hasmethod(obj, meth_name):
"""If it calls like a method it's a method."""
return callable(getattr(obj, meth_name)) if hasattr(obj, meth_name) else False has_methods: (obj, meth_names) ->
name for name in meth_names when obj[name] and obj[name].callMy gut check was this should take about eight lines, plus imports and the class boilerplate. Let's try:
Yep, eight.
[Edit: It occurs to me the Python code might answer "Does this implement all specified methods?" That also takes eight lines in Java. I've appended the implementation above.]
But like the other poster said, you're very unlikely to be doing this in Java, making the whole thing take 0 lines and 129.4 fewer insufferable smugness units.
class ObjectUtil {
static boolean hasMethod(Object obj, String... methodNames) {
for(String methodName : methodNames)
if(!hasMethod(obj, methodName))
return false;
return true;
}
static boolean hasMethod(Object obj, String methodName) {
for(Method method : obj.getClass().getMethods())
if(method.getName().equals(methodName))
return true;
return false;
}
}