mutating method sent to immutable object' in nsmutablearray

1k views Asked by At

I want to remove objects from NSmutableArray can one tell me the Best way to remove from NSMutableArray

.h

@property(nonatomic,retain)NSMutableArray *arr_property;

.m

_arr_property=[[NSMutableArray alloc]init];
MTPop *lplv = [[MTPop alloc] initWithTitle:SelectProperty(APP_SHARE.language)
                                   options:[_arr_property valueForKeyPath:@"property_list.property_type_name"] 
                                   handler:^(NSInteger anIndex) {
    txt_Property.text=[[_arr_property valueForKeyPath:@"property_list.property_type_name"] objectAtIndex:anIndex];
    NSLog(@"index number %ld",(long)anIndex);

remove object--->>>

NSLog(@"index number %@",[_arr_property valueForKey:@"property_list"]);
[[_arr_property valueForKeyPath:@"property_list.property_type_name"] removeObjectAtIndex:anIndex];  ////hear the app is crashing

app is crashing error iam getting is

2015-06-09 13:21:31.104 Estater[2170:62264] *** Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: '-[__NSCFArray removeObjectAtIndex:]: mutating method sent to immutable object'
3

There are 3 answers

3
matt On BEST ANSWER

Think about your code:

_arr_property=[[NSMutableArray alloc]init];

You now have an empty NSMutableArray. It has no elements.

[... removeObjectAtIndex:0];

What did we just say? The array has no elements. It has no element 0 - to have an element 0 it would need to have one element at least, but it doesn't. There is nothing to remove.

[_arr_property valueForKeyPath:@"property_list.property_type_name"]

That part is the weirdest, but let's carry on. When called on an array, valueForKeyPath: results in an NSArray - not an NSMutableArray. So this gives you an empty NSArray. But you cannot say removeObjectAtIndex: to an NSArray, even if it empty - it is not mutable. That's the crash you are experiencing.

2
uraimo On

The real error is that you are calling removeObject on an element of your NSMutableArray:

[-->[_arr_property valueForKeyPath:@"property_list.property_type_name"]<-- removeObjectAtIndex:0]; 

The array looks empty, but if filled with something, to remove the first element you should do instead:

[_arr_property removeObjectAtIndex:0];
2
Akshay Sunderwani On

Firstly, you cannot work with NSMutableArray for key value coding it does not support. You must better use NSMutableDictionary for it. As dictionaries store objects based on a key, whereas arrays store objects based on an index.

You can use NSMutableDictionary like this:

NSMutableDictionary *dict = [NSMutableDictionary dictionary];

[dict setObject:something forKey:@"Some Key"];

// ... and later ...

id something = [dict objectForKey:@"Some Key"];

Secondly, valueForKeyPath: returns a value not array and valueForKey: returns array of value for the key and also that array is not mutable.

Edit:

Thirdly, after researching more on valueForKeyPath:, found its use in collection operation and syntax for using is. So, do it by changing

[_arr_property valueForKeyPath:@"property_list.property_type_name"]

To

[_arr_property valueForKeyPath:@"@property_list.property_type_name"]