user3925713
user3925713

Reputation: 569

call to setter gives unrecognized selector error

I'm trying to subclass NSString to give it a property that is another NSString. No matter what I try with @synthesize or @dynamic or manually coding my setters and getters, I keep getting this "unrecognized selector sent to instance" error when I compile.

I know this has probably already been answered but after looking through about 15 other "unrecognized selector" questions on this site I am still at a loss. Sorry, I started coding VERY recently so I'm probably just missing something exceedingly simple.

Furigana.h

@interface Furigana : NSString

@property (strong, nonatomic) NSString *forKanji;

-(void)setForKanji:(NSString *)forKanji; //fails the same with or without this line

@end

Furigana.m

#import "Furigana.h"

@implementation Furigana
@synthesize forKanji = _forKanji;
//@dynamic forKanji; tried this

-(NSString *)forKanji { //also fails when custom setter/getters are left out
    if(!_forKanji) _forKanji = [[NSString alloc] init];
    return _forKanji;
}

-(void)setForKanji:(NSString *)forKanji {
    if(!_forKanji) _forKanji = [[NSString alloc] init];
    _forKanji = forKanji;
}

@end

Reibun.m

#import "Furigana.h"

-(NSArray *)parseFurigana:(NSArray *)unparsedData {
    NSMutableArray *furigana = [[NSMutableArray alloc] init]; //of Furigana
    for(unsigned int x = 0; x < [unparsedData count]; x++){
        NSArray *components = [[NSArray alloc] init];
        components = [[unparsedData objectAtIndex:x] componentsSeparatedByString:@":"];
        Furigana *newFurigana = [[Furigana alloc] init];
        newFurigana = [components objectAtIndex:1];
        NSLog(@"stored string: %@",newFurigana); //so far so good
        newFurigana.forKanji = [components objectAtIndex:0]; //crash
        //[newFurigana setForKanji:[components objectAtIndex:0]]; //this fails too
        [furigana addObject:newFurigana];
    }
    return furigana;
}

Upvotes: 3

Views: 1148

Answers (1)

Sergey Kalinichenko
Sergey Kalinichenko

Reputation: 726929

Here is the line that breaks your code:

newFurigana = [components objectAtIndex:1];

It replaces the object that you have allocated using [[Furigana alloc] init] with an NSString object, which does not respond to setForKanji: selector.

The assignment replaces newFurigana object, not the content of it. The content cannot be changed, because you derive from NSString, which is immutable.

Replace the init with initWithString, call [super initWithString:] from it, and make the initialization inside your loop look like this:

Furigana *newFurigana = [[Furigana alloc] initWithString:[components objectAtIndex:1]];

Upvotes: 3

Related Questions