Consider following situation:
Object > MyClass > MyClassA, MyClassB
If I want something in the Object level, for example, I added printDetail(); How can I do it in Java implementation? Moreover, can I override all the Object's method. For example, I need to have a whole new .toString(), can I override it? Thanks.
No it cannot, not really anyway. Objective C is a dynamically typed and scoped language, which makes it very amenable to features like categories. The closest you can come to this in Java is class instrumentation via a byte code manipulation library like ASM or Javassist.
But really, when using a strongly typed OO language like Java you should embrace its features rather than trying to duplicate those of another language.
As mentioned in the other answers, there is nothing really like a category. I do have some common solutions I use for some of the categories in my objective-c code when porting over to java. Many of my objective-c categories exist because I don't want to extend the iOS base classes but I do want to add some functionality to that class. Many of those objective-c categories do not add properties using objc_SetAssociatedObject. For those cases I use a static helper class in Java. Let's look at an example using NSString and String. I will add functionality to both to add quotes to the string. We'll assume this is useful and does not exist for the purposes of illustration. In objective-c we might have:
@interface NSString (MyCategory)
/**
* Creates and autoreleased image from self.
*/
- (NSString*)quotedString;
@end
@implementation NSString (MyCategory)
- (NSString *)quotedString
{
return [NSString stringWithFormat:@"\"%@\"", self];
}
@end
You would call this from somewhere like this:
NSString *myString = @"When you're curious, you find lots of interesting things to do.";
NSString *quotedString = [myString quotedString];
Here's how I would implement this in Java:
public class StringHelper {
public static String quotedString(String that) {
return '"' + that + '"';
}
}
And to call it:
String myString = = "When you're curious, you find lots of interesting things to do.";
String quotedString = StringHelper.quotedString(myString);
If you think of the category methods as methods that automatically send the self variable as the first method argument (albeit invisible) then this makes even more sense.
For your example, if I would not extend the specific object, I might do something like:
public class ObjectHelper {
public static void printDetail(Object that) {
// do what it takes;
}
}
UPDATE: A commenter asked for limitations.
Limitations would be that the code is in a separate static class. It's not as convenient as a category. You have to remember those class names, or find them, and you will not get auto completion on your original objects methods in the helper. Also, you cannot use object level properties or attributes like you get with objc_SetAssociatedObject. You could use a hash map and create something similar with the original object instance as a hash key.
public class StringHelper {
private static Map<String, Integer> order = new HashMap();
public static int getOrder(String that) {
if(that == null) { return 0; }
Integer ret = StringHelper.order.get(that);
if(ret == null) { return 0; }
else { return ret; }
}
public static void setOrder(String that, int order) {
if(that != null) {
StringHelper.order.put(that, order);
}
}
}
There are also no name clashes with the original class, which would be more of a benefit. Name clashes in objective-c categories are considered bad.
All Java classes eventually have java.lang.Object
Because of this, all Java classes inherit
methods from Object
. Half of these methods are final
and cannot be overridden
. However, the other methods in Object can be and are overridden
The toString() method in the Object class is used to display some information regarding any object.
So you can Override it according to your self...
EX..
public class Test{
@Override
public String toString() {
/// staff
}
}