Set BOOL value to NSMutableDictionary - iphone

I want to set a BOOL value as true false format to a NSMutableDictionary (which will use as a JSON Dictionary of the API Request). I tried both of the following methods. But those are NOT the correct format requested by the API (API needs the BOOL value as true/false type not as 1/0).
BOOL isDefault = YES;
[dicTemp setValue:[NSString stringWithFormat:#"%c", isDefault] forKey:#"is_default"];
//[dicTemp setValue:[NSNumber numberWithBool:isDefault] forKey:#"is_default"];
Can anyone have an ides

BOOL can be wrapped in an NSNumber object:
dicTemp[#"is_default"] = #YES;
(This code is using the newish Objective-C Literals syntax).
If you are old-fashioned (nothing wrong with that), then the above statement is the same as:
[dicTemp setObject:[NSNumber numberWithBool:YES]
forKey:#"is_default"];
To test later:
NSNumber *numObj = dicTemp[#"is_default"];
if ([numObj boolValue]) {
// it was YES
}

Related

how to set the parameters in dictionary values

I am saving the data in external class file but am getting error while saving the Bool value
as a parameter.
Below is the source code
.savefile.h
-(void) saveDecreasedActivity:(NSInteger) bathing
meal:(NSInteger) meal withTitle:(NSString *)title independentItem:(BOOL)timeItem;
{
NSMutableDictionary *lDataObj = [[NSMutableDictionary alloc] init];
[lDataDict setValue:lSeqCounter forKey:#"seqCounter"];
[lDataObj setValue:timeItem forKey:#"independentItem"];
}
and i have save the data in other class
[saver saveDecreasedActivity:[self.bathingControl selectedSegmentIndex]
meal:[self.mealControl selectedSegmentIndex] withTitle:lTitle independentItem:YES];
It was showing
timeItem is incompatible integer to pointer conversion sending "BOOL" (aka singned char) to parameter of type id
Thanks in advance
You can't store raw types (integers, booleans, etc) in an NSDcitionary, which is a collection of key-value pairs (see docs).
In your case, you can use:
[NSNumber numberWithBool: timeItem];
in:
[lDataObj setValue:[NSNumber numberWithBool: timeItem] forKey:#"independentItem"];
You can only store objects in dictionaries, and BOOL is a type, so you have to wrap it like this:
[dictionary setValue:[NSNumber numberWithBool:aBool] forKey:#"yourKey"];
and retrieve it like this:
BOOL aBool = [[dictionary objectForKey:#"yourKey"] boolValue];
Check the NSNumber class reference for more info.

Objective C - Change all attributes in NSAttributedString?

[attributedString enumerateAttributesInRange:range options:NSAttributedStringEnumerationReverse usingBlock:
^(NSDictionary *attributes, NSRange range, BOOL *stop) {
NSMutableDictionary *mutableAttributes = [NSMutableDictionary dictionaryWithDictionary:attributes];
[mutableAttributes setObject:[NSNumber numberWithInt:1] forKey:#"NSUnderline"];
attributes = mutableAttributes;
}];
I am trying to loop through all attributed and add NSUnderline to them. when debugging it seems like NSUnderline is added to the dictionary, but when i loop for the second time they are removed.
Am I doing anything wrong while updating NSDictionaries?
Jonathan's answer does a good job of explaining why it doesn't work. To make it work, you need to tell the attributed string to use these new attributes.
[attributedString enumerateAttributesInRange:range options:NSAttributedStringEnumerationReverse usingBlock:
^(NSDictionary *attributes, NSRange range, BOOL *stop) {
NSMutableDictionary *mutableAttributes = [NSMutableDictionary dictionaryWithDictionary:attributes];
[mutableAttributes setObject:[NSNumber numberWithInt:1] forKey:#"NSUnderline"];
[attributedString setAttributes:mutableAttributes range:range];
}];
Changing the attributes of an attributed string requires that it is a NSMutableAttributedString.
There is also an easier way to do this. NSMutableAttributedString defines the addAttribute:value:range: method, which sets the value of a specific attribute over the specified range, without changing other attributes. You can replace your code with a simple call to this method (still requiring a mutable string).
[attributedString addAttribute:#"NSUnderline" value:[NSNumber numberWithInt:1] range:(NSRange){0,[attributedString length]}];
You're modifying a local copy of the dictionary; the attributed string does not have any way to see the change.
Pointers in C are passed by value (and thus what they point to is passed by reference.) So when you assign a new value to attributes, the code that called the block has no idea you changed it. The change does not propagate outside of the block's scope.

How can I use an integer value as 'key' to set value in NSMutableDictionary?

How can I use an integer value as 'key' to set a float value in NSMutableDictionary ?
As NSDictionarys are only designed to deal with objects, a simple way to do this is to wrap the integer and float in a NSNumber object. For example:
NSMutableDictionary *testDictionary = [[NSMutableDictionary alloc] init];
[testDictionary setObject:[NSNumber numberWithFloat:1.23f]
forKey:[NSNumber numberWithInt:1]];
NSLog(#"Test dictionary: %#", testDictionary);
[testDictionary release];
To extract the relevant value, simply use the appropriate intValue, floatValue, etc. method from the NSNumber class.
You can use NSMapTable as it supports integer keys and/or values directly. No need to box/unbox through NSNumber, but it is also slightly more difficult to set up and use.
It needs to be an object, so use [NSNumber numberWithInt:myInteger] instead.
Then, retrieve it with -integerValue

Why should I use KVC rather than the simple dot syntax when accessing object properties?

There's the option to go the long way, if an receiver class conforms to the NSKeyValueProtocol:
[myInstance setValue:[NSNumber numberWithInt:2] forKey:#"integerProperty"];
or the short way:
myInstance.integerProperty = 2;
what's the point of this KVC method? When is this useful?
First, those aren't the same, the second should be:
myInstance.integerProperty = [NSNumber numbwerWithInt:2];
if integerProperty is an NSNumber.
In general you use the second form when you are doing the most things. You use setValue:forKey: and valueForKey: when you want to dynamically choose the property to store things in. For instance, think about how valueForKeyPath: against an NSArray works (for reference, if you call -valueForKey: against an NSArray it will return an array where each object is the result of asking the corresponding object in that NSArray for that value:
- (NSArray *) valueForKey:(id)key {
NSMutableArray *retval = [NSMutableArray array];
for (NSObject *object in self) {
[retval addObject:[object valueForKey:key]];
}
return retval;
}
In the above case we were able to use valueForKey: to implement our function even though we do not know what the key is beforehand, since it is passed in as an argument.

Reading data from a plist file

I'm trying to implement a Save State for my iPhone App.
I've got a plist file called SaveData.plist and I can read it in via the following
NSString *pListPath2 = [bundle pathForResource:#"SaveData" ofType:#"plist"];
NSDictionary *dictionary2 = [[NSDictionary alloc] initWithContentsOfFile:pListPath2];
self.SaveData = dictionary2;
[dictionary release];
The Plist file has members
SavedGame which is a Boolean to tell the app if there really is valid data here (if they did not exit the app in the middle of a game, I don't want their to be a Restore Point.
Score which is an NSNumber.
Time which is an NSNumber
Playfield which is a 16 element array of NSNumbers
How do I access those elements inside of the NSDictionary?
Try [NSDictionary objectForKey:]
Where Key is the name of the member in the plist.
For example:
BOOL save = [[dictionary2 objectForKey:#"SavedGame"] boolValue];
will store the object stored in the plist for the key SavedGame into a new BOOL named save.
I imagine that your SavedGame Boolean is actually stored in the NSDictionary as an NSNumber, hence the use of boolValue to get the Boolean Value of the NSNumber.
Try this documentation: Apple NSDictionary Reference.
For Setting Bool Value You can Use :
[Dictionary setBool:TRUE forKey:#"preference"];
For Getting Bool value you can use :
[Dictionary boolForKey:#"preference"];