cannot insert into NSMutableArray due to indexvalue being out of bounds - ios

I have a MutableArray on this view called array and the object in question is detailItem, which has a property of rank (int). On this view, there's a text field displaying the rank and I want to be able to move the detailItem up and down the MutableArray by changing the rank.
So, for example let's say the detailItem has a rank of 3, which is index value of 2. If I change this in the text field to 3, I want the array to adjust and move it down one place. However, as I type in the value of rankField (the text field), it crashes the app since it automatically updates the value before I'm done editing. So, if I click on the text field and write 23 (planing on deleting the 2) or just press delete (now the value is nil) the app crashes with an uncaught exception.
Here's the code:
- (IBAction)rankFIeldTextChanged:(id)sender {
QueueMember *member = self.detailItem;
[self.array removeObjectAtIndex:self.detailItem.rank];
if (0<= [self.rankField.text intValue]<= self.array.count) {
[self.array insertObject:member atIndex:[self.rankField.text intValue]-1];
}
}
The if condition of making the text value in-between the array size and 0 seems to have no effect.
btw this is all in the detailsViewController which is connected to the main view controller via push segue. does it make more sense(or more better coding) to just set the new rank value in details and actually make the array changes in the mainviewcontroller.m?

The problem is that you are trying to do two boolean statements at once (which doesn't work). Change your if statement to something like:
if (0< [self.rankField.text intValue] && [self.rankField.text intValue] < self.array.count) {
//Insert your object here
}
else
{
//Add object here
}
Your current setup check to see if 0<= [self.rankField.text intValue], which will return true for all values greater than or equal to 0. Then it checks the result of that (YES:1, NO:0) if it's less than or equal to your array count. That will always return true if your array has anything in it. So basically your check will always return true.
Since it always returns true I could check for array object number 1000, your if statement says go for it, then I check and the array says "No way in heck!" and crashes your app.
EDIT: Updated my code snippet to take into account your array insertion line.

I'd just do this
- (IBAction)rankFIeldTextChanged:(id)sender {
QueueMember *member = self.detailItem;
[self.array removeObjectAtIndex:self.detailItem.rank];
if ((0<= [self.rankField.text intValue])&&([self.rankField.text intValue]<= self.array.count)) {
if (self.array.count >([self.rankField.text intValue]-1)){
[self.array insertObject:member atIndex:[self.rankField.text intValue]-1];
}
}
}
you are probably trying to insert at an index greater than the count of the array.

Related

Objective C - NSArray's indexOfObject: not work

I use [items indexOfObject:items.lastObject] to get the last index, but this code returns nil. Why does this happen?
The first and last object in your array are both bar button items created with the system item of "fixed space".
The result of calling indexOfObject: is 0, not nil. This means that the object is being found at index 0. indexOfObject: can't return nil. If an object isn't found, it returns the special value NSNotFound which is the unsigned value for -1.
From the documentation for indexOfObject::
Starting at index 0, each element of the array is passed as an argument to an isEqual: message sent to anObject until a match is found or the end of the array is reached. Objects are considered equal if isEqual: (declared in the NSObject protocol) returns YES.
The implementation of UIBarButtonItem isEqual: will return YES if two bar button item instances are created with the same system item (and probably a few other properties as well).
indexOfObject: is not based on the instance of the object, it's based on isEqual:.
If you want to find the index of an object based on the identity (its address) of the object instead of isEqual:, use indexOfObjectIdenticalTo:.
p [items indexOfObjectIdenticalTo:items.lastObject]
will give you 6 instead of 0.

Exception in button tag

I have set the tags for the buttons but in this method i am getting an exception and i am not sure why
- (IBAction)showComments:(UIButton *)sender
{
int tag=[sender tag];
NSLog(#"The tag clicked:%#",[blogids objectAtIndex:tag]);
}
Where blogids is my NSMutableArray
Thanks
You are getting NSRangeException, which means you are trying to retrieve that element of array which is not existing. I suggest you should check the array count with Tag value which you are trying retrieve.
NSLog(#"%d",[blogids count]);
NSLog(#"%#",tag);
I am sure tag value is greater than count. That should not be, if you want to retrieve value from array using tag.
Thanks,
The reason you are getting an exception is because your tag is greater then the blogids count.
Add the buttons to the array and then it will not crash.
For example:
blogids = [[NSMutableArray alloc]init];
[blogids addObject:oneOfYourButtons];
Also if you only want to see the tags number use this:
NSLog(#"The tag clicked:%d",tag);
instead of:
NSLog(#"The tag clicked:%#",[blogids objectAtIndex:tag]);
Your blogids array is blank. Please check if it has object in the index you got from button tag
Your blogids is empty array here. so that, it show as bounds as [0 .. 0](that is array count is zero). Just check your array initialization.

Compare numbers in NSMutableArray with indexPath.row

I have an NSMutableArray that gets edited quite often as a TableView is edited. What I want to do is run a check and see if rows in the TableView match up with any numbers in the NSMutableArray, and if they do, perform an action. So, in the TableView code I have:
if([thearray containsObject:indexPath.row] {
//perform action here
}
However I keep getting the error:
Incompatible integer to pointer conversion sending 'NSInteger' (aka 'int') to parameter of type 'id';
What am I doing wrong and how can I do this?
Use this code...
if([thearray containsObject:[NSNumber numberWithInt:indexPath.row]]) {
//perform action here
}
I think the best you can do here is check if the current count of the array is greater than indexPath.row the (since in theory there will be no gaps in the indexes). The method you are currently calling takes an object and tells you if it is a member of the array. There is also objectAtIndex:, but that raises an exception if the integer you pass is out of bounds.
if(thearray.count > indexPath.row) {
// array has at least indexPath.row + 1 items, so you can get objectAtIndex:indexPath.row
}

iOS Compare Value of Label

I'm using a label to display the string result of function. However I have a class variable that stores the previous result and I need to update that variable in different ways depending on different conditions. The code I wrote is
if(displayPassword.text == #"Memorable")
{
prevpass = [newPassword returnPassword];
}
else
{
prevpass = displayPassword.text;
}
However it always jumps to the else as it seems to show under debugging that displayPassword.text is always empty depsite it showing a value.
You can only use == to compare scalar values. A string is an object. You need to use the isEqual: or isEqualToString: method instead.
if([displayPassword.text isEqualToString:#"Memorable"]) {

xcode check if there is aobjectAtIndex or check array length

I cant find this any where, I may be searching the wrong terms or words but I just need to know how to check if an array is a certain length:
if ([scores objectAtIndex:3]){
//code
}
This comes up with an error and crashes if the array isnt this long yet, but surly this should just check if there is an index, and if not move on??
How to I check this without the app crashing??
count method of NSArray returns the number of objects in the array. If [myArray count] returns n then valid indexes are 0 to n - 1. There is no automatic move on if the index is not valid. Before trying to access an index you need to make sure that the index is valid.
if ([scores count] >= 4) {
id obj = [scores objectAtIndex:3];
}

Resources