Accesing objects in multidimensional array, Obj-c - objective-c

I have an array holding other arrays, but cant get this to work!! IM trying to pull string values from subArrays I can access first the first subarray no problem but then when i try changing the label to the object in second array my prog crashes anyidea on how i should approach this?
int count = 0; // variable to access the required sub array
NSArray* myArray; // array holding other arrays
UILabel* mylabel; // label to display my string values from the array s
-(void) setLabel
{
NSArray* subArray = [myArray objectAtIndex: count];
[myLabel setText:[subArray objectAtIndex:1]]; // this works fine
}
-(void) changeLabelToNextArray
{
count ++
[self setLabel]; //program crashes here when try to load label from next array
}

Why are you doing this?
[myLabel setText:[subArray objectAtIndex:1]];
This will crash if
subArray does not have an object at index 1
the object at index 1 cannot be set as the label text (i.e cannot be made a string)
I think some more information on how your arrays are structured would help give a better answer to what the problem is.
EDIT (Based on comments below)
Try this:
NSArray* myArray; // Contains 5 subarrays, each containing 5 strings
UILabel* myLabel1;
UILabel* myLabel2;
UILabel* myLabel3;
UILabel* myLabel4;
UILabel* myLabel5;
int count = 0; // Keeps track of which subarray we are on
- (void)setLabel
{
NSArray* subArray = [myArray objectAtIndex:count];
[myLabel1 setText: [subArray objectAtIndex:0]]
[myLabel2 setText: [subArray objectAtIndex:1]]
[myLabel3 setText: [subArray objectAtIndex:2]]
[myLabel4 setText: [subArray objectAtIndex:3]]
[myLabel5 setText: [subArray objectAtIndex:4]]
count = (count + 1) % 5; // Ensures that count is always 0 to 4
}
Now whenever you call setLabel, the text should change on all 5 of your labels provided you do indeed have 5 strings in each of the 5 subarrays.

Maybe you can try to use C array :
id myArray[iMax][jMax];
subArray[i][j] = myArray[a][b];

Related

How to get value of NSTextField dynamic add to NSMutableArray?

I have a Combobox contains 30 items (1,2,...,30). I want to select item in Combobox, create dynamic NSTextField same item selected in Combobox. Then user input text to NSTextField, and then click on button to get all text of each NSTextField add to NSMutableArray.
I use bellow code to get text from NSTextField and add it to Array but it can only get from 1 NSTextField:
NSMutableArray * SSID_Arr = [[NSMutableArray alloc] initWithCapacity:x];
[SSID_Arr addObject:ssidtxt.stringValue]; // get text from NSTextField
NSLog (#"SSID_Arr : %#",SSID_Arr);
NSString *strSSID;
for(int j=0; j < [SSID_Arr count]; j++)
{
strSSID = [NSString stringWithFormat:#"\r\nSSID : %#", [SSID_Arr objectAtIndex:j]];
}
Do you have suggestion? Thanks in advance
just make
NSMutableArray *SSID_Arr = [NSMutableArray new];
NSMutableArray * SSID_Arr = [[NSMutableArray alloc] initWithCapacity:x];
gives an array with space reserved for x values.But there is no value in that position right now
So first fill up the array via a loop and then continue as
NSMutableArray * SSID_Arr = [[NSMutableArray alloc] initWithCapacity:x];
for (int i=0; i<x; i++) {
[SSID_Arr addObject:ssidtxt.stringValue];
}
Now the array contains x values and you can proceed.Please note the one textfield value is getting populated here x times.If you have to store all textfield values ,write a loop suitable to achieve all values and add it

NSMutableArray with size of 9

I need to have an NSMutableArray with a constant count of 9 where I can make index-specific insertions and deletions. I know that array = [[NSMutableArray alloc] initWithCapacity:9]; will declare an array with a capacity of 9, but when you get the size of the array, it returns 0.
My first attempt at a solution was to declare an array with capacity 9 (see above) and then fill it with NSNull objects. This code crashes with the error
[NSMutableArray insertObjects:atIndexes:]: array argument is not an NSArray'
- (void) setBlankArray: (NSMutableArray*)array {
for (int i = 0; i < 9; i++) {
[array insertObjects:[NSNull null] atIndexes:i];
}
}
-(void) addCurrentTile: (TileView*)aTile {
[currentTurnTilesArray insertObject:aTile atIndex: aTile.getValue-1];
}
-(void) removeCurrentTile: (TileView*)aTile {
[currentTurnTilesArray removeObjectAtIndex: aTile.getValue-1];
}
Is there a better way to accomplish it?
Not sure what you are trying to accomplish or why, but your removeCurrentTile will break it, because it will reduce the size of the array by 1. What you need to do is wrap this array with a class that guards it such that it can never never never have any other number of elements than 9.
Personally, I think what you're trying to do is silly. If you know you will always have exactly 9 slots, then you should start with a normal array, not a mutable array. It is the objects at each index that you want to mutate - not the array itself. For example, if these things were to be strings, then you would make an immutable array of 9 NSMutableString objects:
NSArray* arr = #[
[NSMutableString string],
[NSMutableString string],
[NSMutableString string],
[NSMutableString string],
[NSMutableString string],
[NSMutableString string],
[NSMutableString string],
[NSMutableString string],
[NSMutableString string]
];
Now each string can be mutated into another value, but no strings can be added or removed such as to change the length of the array.
Of course that's just an example (using strings, I mean). For maximum flexibility, this would be an NSArray of nine NSMutableDictionary objects. Now every NSMutableDictionary can contain anything, or nothing. But the number of NSMutableDictionaries will always be exactly nine, because the array itself is immutable.
You're looking for insertObject:atIndex:, or more simply addObject:.
[[NSMutableArray alloc] initWithCapacity:9] does not create an array with 9 elements.
It creates an empty array initialized with enough memory to hold 9 objects.
The purpose of this method is to allocate that much memory at once as you declare, so you can add elements to this array and system has not to allocate memory every time. This is only for optimization.
NSMutableArray reference
I just read your question, and I think I understand exactly what you need. Here is the code:
Declare a property:
#property (nonatomic, retain) NSMutableArray *myArray;
Synthesize it:
#synthesize myArray = _myArray;
Overrride its getter like this:
- (NSMutableArray *)myArray
{
if (!_myArray)
{
_myArray = [[NSMutableArray alloc] initWithCapacity:9];
for (int i = 0; i < 9; i++)
{
[self.myArray addObject:[NSNull null]];
}
}
return _myArray;
}
The "setBlankArray" method will simly set the property to nil, and next time you call the getter of the array property it will get automatically initialized with exactly what you need:
- (void)setBlankArray:(NSMutableArray *)array
{
self.myArray = nil;
}
VERY IMPORTANT: Do not write this code:
for (int i = 0; i < 9; i++)
{
[self.myArray addObject:[NSNull null]];
}
in the method just mentioned as this will make the array to contain 18 elements.
Then write the other 2 methods:
// you can also change the parameter from "id" to "TileView *"
- (void)addCurrentTile:(id)sender
{
NSInteger tileIndex = 1; // replace 1 with ((TileView *) sender).getValue - 1
[self.myArray replaceObjectAtIndex:tileIndex
withObject:sender];
}
// you can also change the parameter from "id" to "TileView *"
- (void)removeCurrentTile:(id)sender
{
NSInteger tileIndex = 1; // replace 1 with ((TileView *) sender).getValue - 1
[self.myArray replaceObjectAtIndex:tileIndex
withObject:[NSNull null]];
}
But, DO NOT FORGET to replace "id" with "TileView *", and TO SET the value of tileIndex to "((TileView *) sender).getValue - 1".
Hope this all makes sense, and is helpful for you.
Best regards

Load an element value of an array to another array Xcode Objective-C

Here I am getting the cityName1 with the city names like Piscataway, Iselin, Broklyn etc fetched from the tgpList1 array and I need to put the values into an array called item5.
There are 133 records fetched by the above iteration. The following code stores only the last record's cityName1 and not the entire list of city names though inside the loop.
I tried many ways but I am missing something.
tgpList1 is an array.
tgpDAO is an NSObject with two objects NSString *airportCode and NSString *cityName
NSArray *item5 = [[NSArray alloc]init];
for (int currentIndex=0; currentIndex<[tgpList1 count]; currentIndex++)
{
tgpDAO *tgpTable = (tgpDAO *)[self.tgpList1 objectAtIndex:currentIndex];
NSLog(#"The array values are %#",tgpList1);
NSString *cityName1 = tgpTable.cityName;
item5 =[NSArray arrayWithObjects:cityName1, nil];
}
Use mutable array.
{
NSMutableArray *item5 = [[NSMutableArray alloc]initWithArray:nil];
for (int currentIndex=0; currentIndex<[tgpList1 count]; currentIndex++) {
tgpDAO *tgpTable = (tgpDAO *)[self.tgpList1 objectAtIndex:currentIndex];
NSLog(#"The array values are %#",tgpList1);
NSString *cityName1 = tgpTable.cityName;
[item5 addObject:cityName1];
}
}
Instead of
item5 =[NSArray arrayWithObjects:cityName1, nil];
use
[item5 addObject:cityName1];
There are more ways of achieving that. However, this is the one that is designed for that purpose and the most "readable" from my pont of view.
If you need to clear the contents of item5 before then call
[item5 removeAllObjects];
right before the for loop.
What you were doing: arrayWithObjects allways creates a new array that ist made of the objects that are passed to it as aguments. If you do not use ARC, then you would create some serious memory leak with your code because arrayWithObjects creates and retains an object on every loop and on the next loop all references to the array object, that was just created, are lost without being released. If you do ARC then you do not have to worry about in this case.
NSMutableArray *myCities = [NSMutableArray arrayWithCapacity:2]; // will grow if needed.
for( some loop conditions )
{
NSString* someCity = getCity();
[myCities addObject:someCity];
}
NSLog(#"number of cities in array: %#",[myCities count]);

trying to loop through nested array , obj-c

I have an array with 5 sub arrays that I'm trying to loop through,
I can access the first sub array and its objects but when I increase the variable count and try to access the second sub array my program crashes any ideas on a better way to do this? This is the my general method:
-(void) accessArray {
NSArray *myArray; // my array that holds sub arrays
int count = 0; //used to hold which sub array im accesing
NSArray *subArray = [myArray objectAtIndex:count];
//do something with object = [subArray objectAtIndex:0];
//do something with object = [subArray objectAtIndex:1];
}
-(void) otherMethod {
count ++
[self accessArray];
}
for (NSArray *inner in outerArray)
for (id object in inner) {
... do stuff ...
}
}
In addition to bbums answer you can make sub arrays using NSRange (example from NSArray Class Reference):
NSArray *halfArray;
NSRange theRange;
theRange.location = 0;
theRange.length = [wholeArray count] / 2;
halfArray = [wholeArray subarrayWithRange:theRange];
Only saying this because it looks like this might be what you are trying to do. This doesn't iterate through objects, but it is handy when trying to make new arrays from others.
If you REALLY want to do it using your way (i.e. access the subarrays through 'otherMethod'), you'll need to make the 'count' variable accessible to both methods:
int count = 0; // used to hold which sub array I'm accessing
-(void) accessArray {
NSArray *myArray; // my array that holds sub arrays
NSArray *subArray = [myArray objectAtIndex:count];
// do something with object = [subArray objectAtIndex:0];
// do something with object = [subArray objectAtIndex:1];
}
-(void) otherMethod {
count++; // Cannot access count if defined inside 'accessArray'
[self accessArray];
}
Now you can use 'otherMethod' to access the subarrays. But I think the best way to do this is already given in the first answer above by bbum.

How to change this so that it returns arrays

The following code works perfectly and shows the correct output:
- (void)viewDidLoad {
[super viewDidLoad];
[self expand_combinations:#"abcd" arg2:#"" arg3:3];
}
-(void) expand_combinations: (NSString *) remaining_string arg2:(NSString *)s arg3:(int) remain_depth
{
if(remain_depth==0)
{
printf("%s\n",[s UTF8String]);
return;
}
NSString *str = [[NSString alloc] initWithString:s];
for(int k=0; k < [remaining_string length]; ++k)
{
str = [s stringByAppendingString:[[remaining_string substringFromIndex:k] substringToIndex:1]];
[self expand_combinations:[remaining_string substringFromIndex:k+1] arg2:str arg3:remain_depth - 1];
}
return;
}
However, instead of outputting the results, I want to return them to an NSArray. How can this code be changed to do that? I need to use the information that this function generates in other parts of my program.
There are several things that you need to change in your code.
First - consider changing the name of your method to something more legible and meaningful than -expand_combinations:arg2:arg3.
Second - you have a memory leak. You don't need to set allocate memory and initialize str with the string s, because you change its value right away in the loop without releasing the old value.
Third - take a look at NSMutableArray. At the beginning of the method, create an array with [NSMutableArray array], and at every line that you have printf, instead, add the string to the array. Then return it.
basicaly you have:
create mutable array in viewDidLoad before [self expand_combinations ...
add aditional parameter (mutable array) to expand_combinations
populate array in expand_combinations