Когда использовать двоеточие с @selector - PullRequest
12 голосов
/ 10 февраля 2011

Просто приступаю к разработке для iPhone и Objective-C.

Вчера я пытался добавить Observer для уведомления в моем представлении, и я продолжал получать эту ошибку:

unrecognized selector sent to instance

Я отследил это до того факта, что мне нужно было добавить конечную двоеточие к аргументу селектора:

[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(nameOfMySelector:) name:@"BBLocationServicesAreDisabled" object:nil];

Сегодня я подумал, что был умен, потому что при настройке аргумента действия для кнопки я вспомнилмоя ошибка вчера, и добавил двоеточие к аргументу действия.Аргумент действия принимает @selector, так же, как аргумент селектора при настройке наблюдателя для NSNotification, поэтому я решил, что поступаю правильно.

Однако со следующим кодом:

[self.callToActionButton addTarget:self action:@selector(nameOfMySelector:) forControlEvents:UIControlEventTouchUpInside];

Я получаю точно такую ​​же ошибку:

unrecognized selector sent to instance

Что дает?Почему один @selector требует в конце двоеточия, а другой нет?Каким правилам я должен следовать, когда он должен быть включен, и когда он должен быть остановлен, и почему я не могу всегда делать одно или другое?

Спасибо!

Ответы [ 6 ]

30 голосов
/ 10 февраля 2011

Как упоминалось в boltClock, персонаж, на которого вы ссылаетесь, на самом деле является двоеточием.Разница между @selector(method) и @selector(method:) заключается в сигнатуре метода.Во втором варианте ожидается, что параметр будет передан.

@selector(method) ожидает метод: -(void)method

@selector(method:) ожидает метод: -(void)method:(id)someParameter

8 голосов
/ 10 февраля 2011

Кажется, вам здесь не хватает одного понятия: двоеточие, в некотором смысле, является частью имени метода.Например, метод

-(IBAction) doIt:(id)sender;

имеет имя doIt:.Таким образом, двоеточие должно использоваться для ссылки на этот метод.
Но этот метод не имеет двоеточия в конце

-(IBAction) doItWithoutParameter;

То же самое относится и к методам, принимающим несколько аргументов, они имеют имена типа doItWithParam1:andParam2:

6 голосов
/ 10 февраля 2011

Селектор представляет имя метода, а число двоеточий в селекторе соответствует количеству аргументов в соответствующем методе:

  1. mySelector - без двоеточия, без аргументов, например, - (void)mySelector;, [self mySelector];
  2. mySelectorWithFoo: - одно двоеточие, один аргумент, например - (void)mySelectorWithFoo:(Foo *)foo;, [self mySelectorWithFoo:someFoo];
  3. mySelectorWithFoo:withBar: - два двоеточия, два аргумента, например - (void)mySelectorWithFoo:(Foo *)foo bar:(Bar *)bar;, [self mySelectorWithFoo:someFoo bar:someBar];

и т. Д.

Также можно использовать селектор без «именования» параметров.Это не рекомендуется, поскольку не сразу понятно, какие параметры:

  1. mySelector:: - два двоеточия, два аргумента, например, - (void)mySelector:(Foo *)foo :(Bar *)bar;, [self mySelector:someFoo :someBar];
  2. mySelector::: -три двоеточия, три аргумента, например - (void)mySelector:(int)x :(int)y :(int)z;, [self mySelector:2 :3 :5];
2 голосов
/ 10 февраля 2011

В вашем случае:

[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(nameOfMySelector:) name:@"BBLocationServicesAreDisabled" object:nil];

- (void) nameOfMySelector: (NSNotification *) notification {
    /* this method would require the semi-colon */
}

или в этом случае:

[self.callToActionButton addTarget:self action:@selector(nameOfMySelector:) forControlEvents:UIControlEventTouchUpInside];

- (void) nameOfMySelector: (id) sender {
    /* this method would also require the semi-colon */
}
2 голосов
/ 10 февраля 2011

Двоеточие указывает, что метод принимает параметр.

[someObject performSelector:@selector(doSomething:)] означает, что doSomething ожидает параметр.

[someObject performSelector:@selector(doSomething)] означает, что doSomething не нуждается ни в каких параметрах.

0 голосов
/ 10 февраля 2011

Я думаю, что проблема в пропущенном параметре.

Смотрите этот пост: Objective-C: вызов селекторов с несколькими аргументами (Отличные ответы!)

...