Objective-C'de, son bileşenin bir argüman almadığı durumlarda yöntem adlarını bildiremezsiniz. Örneğin, aşağıdaki yasa dışıdır.
-(void)take:(id)theMoney andRun;
-(void)take:(id)yourMedicine andDontComplain;
Objective-C neden bu şekilde tasarlandı? Kimsenin kurtulmaya ihtiyaç duymadığı, Smalltalk'ın bir eseri miydi?
Bu sınırlama Smalltalk'da anlamlıdır, çünkü Smalltalk mesaj çağırma etrafında sınırlayıcılara sahip değildir, bu nedenle son bileşen, son argümana tek bir mesaj olarak yorumlanacaktır. Örneğin, BillyAndBobby take:'$100' andRun
olarak ayrıştırılır BillyAndBobby take:('$100' andRun)
. Köşeli parantezlerin gerekli olduğu Objective-C'de bu önemli değildir.
Parametresiz seçici bileşenlerin desteklenmesi, bir programcının seçtiği yöntem adı olarak (örneğin runWith:
,take:andRun
) bir programın işlevsel anlamını veya dilin ifade gücünü etkilemez. Gerçekte, parametresiz bileşenlere sahip bir program, içermeyen bir programın alfa eşdeğeridir. Bu nedenle, böyle bir özelliğin gerekli olmadığını belirten yanıtlarla ilgilenmiyorum (Objective-C tasarımcılarının belirtilen nedenleri bu değilse; Brad Cox veya Tom Love'ı tanıyan var mı? Burada mı?) özelliğe gerek kalmaması için yöntem adlarının nasıl yazılacağı. Birincil fayda, okunabilirlik ve yazılabilirliktir (ki bu okunabilirlik gibidir, sadece ... bilirsiniz), çünkü bu, doğal dil cümlelerine daha çok benzeyen yöntem isimleri yazabileceğiniz anlamına gelir. Sevmez -(BOOL)applicationShouldTerminateAfterLastWindowClosed:(NSApplication*)theApplication
ki Matt Gallagher işaret ( "Kakao With Love" üzerine-(BOOL)application:(NSApplication*)theApplication shouldTerminateAfterLastWindowClosed
, böylece parametre hemen uygun ismin yanına yerleştirilir.
Apple'ın Objective-C çalışma zamanı (örneğin) bu tür seçicileri mükemmel şekilde idare edebilir, öyleyse neden derleyici olmasın? Neden onları yöntem adlarında da desteklemiyorsunuz?
#import <Foundation/Foundation.h>
#import <objc/runtime.h>
@interface Potrzebie : NSObject
-(void)take:(id)thing;
@end
@implementation Potrzebie
+(void)initialize {
SEL take_andRun = NSSelectorFromString(@"take:andRun");
IMP take_ = class_getMethodImplementation(self, @selector(take:));
if (take_) {
if (NO == class_addMethod(self, take_andRun, take_, "@@:@")) {
NSLog(@"Couldn't add selector '%@' to class %s.",
NSStringFromSelector(take_andRun),
class_getName(self));
}
} else {
NSLog(@"Couldn't find method 'take:'.");
}
}
-(void)take:(id)thing {
NSLog(@"-take: (actually %@) %@",NSStringFromSelector(_cmd), thing);
}
@end
int main() {
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
Potrzebie *axolotl=[[Potrzebie alloc] init];
[axolotl take:@"paradichloroaminobenzaldehyde"];
[axolotl performSelector:NSSelectorFromString(@"take:andRun")
withObject:@"$100"];
[axolotl release];
[pool release];
return 0;
}