たとえば、Objective-Cクラスのメソッドはオーバーライドできますが、Javaはオーバーライドできないことを私は知っています。
これの利点は何ですか?他にどのような違いがありますか?
たとえば、Objective-Cクラスのメソッドはオーバーライドできますが、Javaはオーバーライドできないことを私は知っています。
これの利点は何ですか?他にどのような違いがありますか?
一言で言えば、Javaの静的メソッドは、クラスにアタッチされた関数にすぎません。これやスーパーを使用できないという点で、インスタンスメソッドのようには機能しません。彼らは事実上、彼らがクラスにいるという本当の概念を持っていません。
ただし、Objective-Cクラスのメソッドは大きく異なります。これらは、クラスを除いて、インスタンスメソッドとまったく同じです。クラスがObj-Cのオブジェクトであることを考えると、これはそれほど驚くべきことではありません。そのため、それらはすべて同じ動的ディスパッチを通過するため、selfを使用して他のクラスメソッドにアクセスしたり、superを使用してスーパークラスのクラスメソッドを呼び出すことができます。これにより、nilメッセージング、メソッドスウィズリングなど、インスタンスメソッドで実行できるのと同じことをすべてクラスメソッドで実行できるため、柔軟性が大幅に向上します。
マークピルキントンの答えは正しいです。これは、Objective-Cクラスのメソッドではできるが、Javaの静的メソッドではできないことを示す具体的な例です。
@interface Parent : NSObject
+ (int)foo;
+ (int)bar;
- (void)printMyFoo;
@end
@interface Child : Parent
+ (int)bar; // Override bar only.
@end
@implementation Parent
+ (int)foo {
return [self bar];
}
+ (int)bar {
return 0;
}
- (void)printMyFoo {
NSLog(@"%d", [[self class] foo]);
}
@end
@implementation Child
+ (int)bar {
return 1;
}
@end
これprintMyFoo
で、親と子のインスタンスを呼び出すと、実行時に呼び出しが+[Parent foo]
動的にディスパッチされるため、異なる結果が得られます。bar
id parent = [[Parent alloc] init];
id child = [[Child alloc] init];
[parent printMyFoo]; // -> 0
[child printMyFoo]; // -> 1
class Parent {
static int foo() { return bar(); }
static int bar() { return 0; }
void printMyFoo() { System.out.println(foo()); }
}
class Child extends Parent {
static int bar() { return 1; }
}
printMyFoo()
これで、親と子のインスタンスを呼び出すと、両方とも同じものを出力します。これは、子の場合でも、次の代わりにParent.foo()
呼び出すためです。Parent.bar()
Child.bar()
Parent parent = new Parent();
Child child = new Child();
parent.printMyFoo(); // -> 0
child.printMyFoo(); // -> 0
これは、Oracle(元々はSun)のJavaドキュメントがクラス変数とメソッドについて述べていることです:http://download.oracle.com/javase/tutorial/java/javaOO/classvars.html