I have NSMutableArray like :
NSMutableArray *x=[[NSMutableArray alloc]initWithObjects:#"a",#"b",#"c",#"d", nil];
NSLog(#"%#",x.description);
From the description I got the following result :
(
a,
b,
c,
d
)
I want to again recreate the array from the description is it possible ?
There is no way that would reliably work in all cases. For example, you cannot know if
(
123
)
represents an array containing a string or a number.
Added: There actually is a method to convert the description back to an array object (but it does not always return an identical array for the reason given above). The description method of NSArray and NSDictionary
uses the Old-Style ASCII Property Lists format which can be read using NSPropertyListSerialization:
NSArray *a1 = #[#"123", #456];
NSString *desc = [a1 description];
NSData *d = [desc dataUsingEncoding:NSUTF8StringEncoding];
NSArray *a2 = [NSPropertyListSerialization propertyListWithData:d
options:0
format:NULL
error:NULL];
NSLog(#"%#", a2);
NSLog(#"a1[1] is a %#", [a1[1] class]);
NSLog(#"a2[1] is a %#", [a2[1] class]);
Output:
(
123,
456
)
a1[1] is a __NSCFNumber
a2[1] is a __NSCFString
As you can see, the array a2 looks like a1, but the second element 456, which was a NSNumber originally, has been read back as a NSString.
So you should use description only as a debugging tool. Better methods to create a reversible human-readable description or an archive have been mentioned in the other answers and comments.
While you could, it's not why NSLog() exists. NSLog's purpose is to give a simple error logging mechanism for developers.
You should read into other means of storing data :
Saving to file via NSData.
Using Core Data
NSCoder
Various JSON serializers/parsers.
etc.
But if you really want to, you could parse a log file manually. (With NSRegularExpressions perhaps, NSScanner, etc.)
Related
hey just a couple quick noob questions about writing my first ios app. Ive been searching through the questions here but they all seem to address questions more advanced than mine so im getting confused.
(1) All I want to do is turn a string into an array of integers representing the ASCII code. In other words, I want to convert:
"This is some string. It has spaces, punctuation, AND capitals."
into an array with 62 integers.
(2) How do I get back from the NSArray to a string?
(3) Also, are these expensive operations in terms of memory or computation time? It seems like it might be if we have to create a new variable at every iteration or something.
I know how to declare all the variables and im assuming I run a loop through the length of the string and at each iteration I somehow get the character and convert it into a number with some call to a built in command.
Thanks for any help you can offer or links to posts that might help!
if you want to store the ascii values in an nsarray it is going to be expensive. NSArray can only hold objects so you're going to have to create an NSNumber for each ASCII value:
unsigned len = [string length];
NSMutableArray arr = [NSMutableArray arrayWithCapacity:len];
for (unsigned i = 0; i < len; ++i) {
[arr addObject:[NSNumber numberWithUnsignedShort:[string characterAtIndex:i]]];
}
2) to go back to an NSString you'll need to use an MSMutableString and append each byte to the NSMutableString.
After saying that I'd suggest you don't use this method if you can avoid it.
A better approach would be to use #EmilioPelaez's answer. To go back from a memory buffer to an NSString is simple and inexpensive compared to iterating and concatting strings.
NSString * stringFromMemory = [[NSString alloc] initWithBytes:buffer length:len encoding: NSASCIIStringEncoding];
I ended up using the syntax I found here. Thanks for the help
How to convert ASCII value to a character in Objective-C?
NSString has a method to get the characters in an array:
NSString *string = "This is some string. It has spaces, punctuation, AND capitals.";
unichar *buffer = malloc(sizeof(unichar) * [string lenght]);
[string getCharacters:buffer range:NSMakeRange(0, [string length])];
If you check the definition of unichar, it's an unsigned short.
I assign JSON values to NSDictionary and try to retrive Key's from the dictionary. It returns the value with the parentheses!
This is the value it returns
(
873
) , (
"HST 299"
)
Here is the JSON
[{"_id":873,"_code":"HST 299"}]
Here is my code:
NSDictionary *courseDetail = [responseString JSONValue];
NSLog(#"%# , %#", [courseDetail valueForKey:#"_id"], [courseDetail valueForKey:#"_code"]);
Because your JSON is an array ([] means array).
And there is ONE dictionary with TWO key-values in the array.
So, if you change your code into
NSDictionary *courseDetail = [[responseString JSONValue] objectAtIndex:0];
it will gives you the correct result.
Parentheses are how NSArrays describe themselves. Your values are apparently arrays that each contain a single string, not bare strings.
I have 2 doubles with each iteration I want add to a NSMutableArray but I can't seem to make it happen.
NSMutableArray *touchArray = [[NSMutableArray alloc]init];
[touchArray addObject:[NSString stringWithFormat:#"%d", "%d", tapTotal, touchBegin]];
NSLog(#"array: %#", touchArray);
The console prints 14108 as the value for the array, I'm not sure where that's coming from, it's not the value of either on of the variables. And XCode complains on the first two lines, "local declaration of 'touchArray' hides instance variable. I know I'm doing at least one thing wronl
Thanks for any help,
Robert
first, the 'local declaration problem':
You have already declared touchArray elsewhere, therefore you don't need to redeclare, just (possibly) initialize like so touchArray = [[NSMutableArray alloc] init];
Secondly: the double problem: theres quite a few:
you are adding a string to the array, not two doubles. to add a double, you need to wrap it in an NSNumber first:
[touchArray addObject:[NSNumber numberWithDouble:firstDouble]];
[touchArray addObject:[NSNumber numberWithDouble:secondDouble]];
also you want to print out each variable in the array to check it I would believe, not the array object itself. for this: NSLog(#"array[0] = %g", [[touchArray objectAtIndex:0] doubleValue]
edit for answer clarification: my answer assumes the poster wants to add two doubles seperately to the array, not a string with two values in it. Thought i might clear that up as kenny and I had different outtakes :)
there is a lot wrong here, so I would suggest maybe trying to read an objective c/iphone development book to learn more.
You are using +stringWithFormat: wrongly. Only the first string can be the format string. The rest will be passed as parameter to format. In your code, the format string is "%d", so the runtime will expect exactly 1 integer. It sees the address to the 2nd "%d" is 14108, so it will print this as an integer.
The correct code should be:
[NSString stringWithFormat:#"%g %g", tapTotal, touchBegin]
(Usually, %d → int, %u → unsigned, %g → double and CGFloat, %# → Objective-C objects, etc.)
"local declaration of 'touchArray' hides instance variable" shows you already have defined same array anywhere else in the code locally. Or you defined it into your .h file
NSLog cant directly print what you have inside a array. If you added a string as its first object (i.e. index 0) then you should print like this-
NSLog(#"array: %#", [touchArray objectAtIndex:0]);
Cheers
I'm writing an NSString to a plist file but after its written to the plist, and when I try to open i get the following message
"This document "mylist.plist" could not be opened XML parser error: Unexpected character 2 at line 1 Old-style plist parser error: Unexpected';' or '=' after key at line 1"
Here is my code:
NSString *temp = [NSString stringWithFormat:#"%#\n Selection is %# \n %d for %.2lf = %.2lf", [NSDate date], #"IPC", 2, 42.34, 2 * 42.34];
[temp writeToFile:[self getPathName:#"mylist.plist"] atomically:YES];
any help would be appreciated.
Thanks,
-[NSString writeToFile...] does not create a plist. It creates a text file. There is no such thing as "writing a string to a plist". Only NSArray and NSDictionary objects can be written to plist files. Those can then contain NSString objects (and other objects, like NSDate and NSData, etc), but what you're asking for is not possible.
For more information, check out the Property List Programming Guide.
Edit: I should clarify what I mean by "creating a plist". When I say that, I'm referring to the XML documents defined by the Apple Plist DTD: http://www.apple.com/DTDs/PropertyList-1.0.dtd
%#\n Selection is %# \n %d for %.2lf = %.2lf is definitely not in any plist format. If you want to retain the plist format, use +[NSPropertyListSerialization dataFromPropertyList:...] to convert the string into data as a plist, then save the data.
And I don't see a reason to use plist if you're only storing 1 string. You can simply save as a .txt and load it using +[NSString stringWithContentsOfFile:...].
I am writing a string tokenizer in Objective-C for an iPhone application.
I have the result as:
1|101|Y|103|Y|105|Y|107|Y|109|Y|111|Y|113|Y|115|Y|
I want to tokenize this string and display each of the values in tabular format. How am I to do it?
I want the result in a tabular format. Like:
102 Y
103 Y
.. ...
If by “tokenizing” you mean simply “splitting on the pipe-sign”, you can use the componentsSeparatedByString: method of NSString:
NSString *original = #"1|101|Y|103|Y|105…";
NSArray *fields = [original componentsSeparatedByString:#"|"];
“Displaying in a tabular format” doesn’t say much. If you want a classic table, see the UITableView class.
Not sure why you want this specifically in Objective-C (are you looking for a
tokenizer class?), but generic strsep() resp. iso-c90 strtok() / strtok_r() do this and they exist on Mac OS X and on iPhone OS. Described here:
http://developer.apple.com/iPhone/library/documentation/System/Conceptual/ManPages_iPhoneOS/man3/strsep.3.html
These got code quotes as well.
NSString *string = #"1|101|Y|103|Y|105|Y|107|Y|109|Y|111|Y|113|Y|115|Y|";
NSArray *chunks = [string componentsSeparatedByString: #"|"];