I need to extract the different components from a GPS coordinate string. So for example:
+30° 18' 12" N // pull out 30, 18 & 12
or
+10° 11' 1" E // pull out 10, 11 & 1
or
-3° 1' 2" S // pull out -3, 1 & 2
or
-7° 12' 2" W // pull out -7, 12 & 2
I have had a look around online and I notice there is the NSRegularExpression. I was wondering if it's possible to use this in some way? I have also had a look at the documentation provided and I have tried to put together a regex to pull out the different parts. This is what I came up with:
('+'|'-')$n°\s$n'\s$n"\s(N|E|S|W)
I'm not really sure if this is correct or not, I'm also unclear on how to use it since there aren't many tutorials/example around. Please could someone help me out? If there is a better way of doing this rather than using NSRegularExpression I'm open to it, however as far as I'm aware objective c does't have any built in regex support.
RegExps are an overkill, IMHO. Use [NSString componentsSeparatedByString:] with space as the separator to split the string into parts, then [NSString intValue] to tease the numeric value of each component except for the last one.
Using NSScanner:
NSScanner *scanner;
NSCharacterSet *numbersSet = [NSCharacterSet characterSetWithCharactersInString:#" °'"];
int degrees;
int minutes;
int seconds;
NSString *string = #" -7° 12' 2\" W";
scanner = [NSScanner scannerWithString:string];
[scanner setCharactersToBeSkipped:numbersSet];
[scanner scanInt:°rees];
[scanner scanInt:&minutes];
[scanner scanInt:&seconds];
NSLog(#"degrees: %i, minutes: %i, seconds: %i", degrees, minutes, seconds);
NSLog Output:
degrees: -7, minutes: 12, seconds: 2
RE's overkill (Seva)? How about objects? ;-)
NSString *coords = #"+30° 18' 12\" N";
int deg, sec, min;
char dir;
if(sscanf([coords UTF8String], "%d° %d' %d\" %c", °, &min, &sec, &dir) != 4)
NSLog(#"Bad format: %#\n", coords);
else
NSLog(#"Parsed %d deg, %d min, %d sec, dir %c\n", deg, min, sec, dir);
Whether you like this depends on your view of dropping into C, but it is direct and simple.
NSMutableArray *newCoords = [[NSMutableArray alloc] init];
NSArray *t = [oldCoords componentsSeparatedByString: #" "];
[newCoords addObject: [[t objectAtIndex: 0] intValue];
[newCoords addObject: [[t objectAtIndex: 1] intValue];
[newCoords addObject: [[t objectAtIndex: 2] intValue];
Assuming you had the coordinates given in your post in NSString oldCoords, this would result in an NSMutableArray called newCoords which would contain the three pieces of data you need.
The re you need is: #"([+-]?[0-9]+)"
Here is example code:
NSString *string;
NSString *pattern;
NSRegularExpression *regex;
NSArray *matches;
pattern = #"([+-]?[0-9]+)";
regex = [NSRegularExpression
regularExpressionWithPattern:pattern
options:NSRegularExpressionCaseInsensitive
error:nil];
string = #" -7° 12' 2\" W";
NSLog(#"%#", string);
matches = [regex matchesInString:string options:0 range:NSMakeRange(0, [string length])];
degrees = [[string substringWithRange:[[matches objectAtIndex:0] range]] intValue];
minutes = [[string substringWithRange:[[matches objectAtIndex:1] range]] intValue];
seconds = [[string substringWithRange:[[matches objectAtIndex:2] range]] intValue];
NSLog(#"degrees: %i, minutes: %i, seconds: %i", degrees, minutes, seconds);
NSLog output:
degrees: -7, minutes: 12, seconds: 2
Related
How to remove string from the original one
i.e. my string is,
series0001.0001
or
series0010.0101
or
series0110.0050
from this string I have to convert it to
expected result
Series 1 1
Series 10 101
Series 110 50
This is the code stuff which I am doing
NSArray * words = [sym.data componentsSeparatedByString:#"\r\n\r\n"];
NSLog(#"words are %#",words);
NSString *strSeriesAndLabelDetail = [words objectAtIndex:0];
NSLog(#"strSeriesAndLabelDetail is %#",strSeriesAndLabelDetail);
NSArray *wordsToSeparateSeriesAndLabel = [strSeriesAndLabelDetail componentsSeparatedByString:#"."];
NSLog(#"wordsSeriesLabel are %#",wordsToSeparateSeriesAndLabel);
strLabelNumber = [wordsToSeparateSeriesAndLabel objectAtIndex:1];
NSLog(#"strLabelNumber are %#",strLabelNumber);
strSeriesNumber = [wordsToSeparateSeriesAndLabel objectAtIndex:0];
NSLog(#"strSeriesNumber is %#",strSeriesNumber);
Current OutPut is:
words are (
"series0001.0003",
"Use the Sort-a-Cord app to read this code or visit www.sortacord.com to get your Sort-a-Cords."
)
strSeriesAndLabelDetail is series0001.0003
wordsSeriesLabel are (
series0001,
0003
)
strLabelNumber are 0003
strSeriesNumber is series0001
Can anybody help me out. Thanks in advance for any suggestion.
A way to do it:
NSString *stringToModify = #"series0110.0050";
stringToModify = [stringToModify stringByReplacingOccurrencesOfString:#"series" withString:#""];
NSArray *array = [stringToModify componentsSeparatedByString:#"."];
NSString *finalString = [NSString stringWithFormat:#"Series %d %d", [[array objectAtIndex:0] integerValue], [[array objectAtIndex:1] integerValue]];
NSLog(#"%#",finalString);
Note that it maybe modified according to what you really want. I assumed that you got always "series" to look for.
I have an NSString *string=#"606" and I want to add a ":" colon after two digits.
The output should look like this: 6:06
It this is possible?
Help would be appropriated.
Thank you very much.
You can add the column between the hours and the minutes like this:
NSString *string = #"606";
NSString *result = [string stringByReplacingCharactersInRange:NSMakeRange(string.length-2, 0) withString:#":"];
NSLog(#"%#", result);
This will give the following results
#"606" => #"6:06"
#"1200" => #"12:00"
#"1406" => #"14:30"
Note: This will only work if the string has 3 or 4 characters, but this is the case according to your question.
Because you do not have two separate objects for hours and minutes, use:
NSString *newTimeString, *hour, *minute;
NSUInteger length = [timeString length];
if (length == 3)
{
hour = [timeString substringToIndex:1];
minute = [timeString substringFromIndex:2];
}
else
{
hour = [timeString substringToIndex:2];
minute = [timeString substringFromIndex:3];
}
newTimeString = [NSString stringWithFormat:#"%#:%#", hour, minute];
I used a long version to illustrate the concept. Basically, use the length of the original string (timeString) to extract the time components and combine them with a colon.
Will it be 2 digits no matter what? Otherwise you could build your custom string from parameters.
NSString *string = [NSString stringWithFormat:#"%#:%#", hours, minutes];
UPDATE
If you just need to add a colon after 1 char, you can do it this way. Although I would suggest finding a safer method as this could be inaccurate if you have a double digit hour.
NSString *hour = [NSString substringToIndex:1]; // double check the index
NSString *min = [NSString substringFromIndex:1]; // double check the index
NSString *time = [NSString stringWithFormat:#"%#:%#", hour, min];
Hopefully this will help.
NSString * str=[zoneDict objectForKey:#"name"];
NSLog(#"==========string zone::==========%#",str);
// str="(GMT +3:00) Baghdad, Riyadh, Moscow, St. Petersbur";
How can I get the 3:00 value from the above string?
NSString *str = #"(GMT -3:00) Baghdad, Riyadh, Moscow, St. Petersbur";
NSRange endRange = [str rangeOfString:#")"];
NSString *timeString = [str substringWithRange:NSMakeRange(5, endRange.location-5)];
NSRange separatorRange = [timeString rangeOfString:#":"];
NSInteger hourInt = [[timeString substringWithRange:NSMakeRange(0, separatorRange.location)] intValue];
NSLog(#"Hour:%d",hourInt);
Rather than trying to extract the time offset from the string, is there any way you could store actual time zone data in your zoneDict? For example you could store NSTimeZone instances instead.
If all you have is the string, you could use an NSRegularExpression object and extract the relevant information using a regular expression instead.
If you could explain further what you're trying to do then there may be an alternative way to achieve what you want.
I like to use -[NSString componentsSeparatedByString]:
NSString *str = #"(GMT -3:00) Baghdad, Riyadh, Moscow, St. Petersbur";
NSArray *myWords = [myString componentsSeparatedByString:#")"];
NSString *temp1 = [myWords objectAtIndex:0];
if ([temp1 rangeOfString:#"-"].location == NSNotFound) {
NSArray *temp2 = [temp1 componentsSeparatedByString:#"+"];
NSString *temp3 = [temp2 objectAtIndex:1];
NSLog(#"Your String - %#", temp3);
}
else {
NSArray *temp2 = [temp1 componentsSeparatedByString:#"-"];
NSString *temp3 = [temp2 objectAtIndex:1];
NSLog(#"Your String - %#", temp3);
}
Output:
Your String - 3:00
Using regular expressions is the better option in my view (if you are forced to extract the '3' only). The regular expression string would contain something like "\d?" but don't quote me on that, you'll have to look up the exact string. Perhaps someone on here could provide the exact string.
In objective c how to Remove text after a string occurrence.
for example i have to remove a text after occurrence of text 'good'
'iphone is good but..' here i have to remove the but text in the end so the text will be now 'iphone is good'
Try with below code
NSString *str_good = #"iphone is good but...";
NSRange range = [str_good rangeOfString:#"good"];
str_good = [str_good substringToIndex:range.location+range.length];
NSString * a = #"iphone is good but..";
NSRange match = [a rangeOfString:#"good"];
NSString * b = [a substringToIndex:match.location+match.length];
If you want to remove rest of the string after a particular occurrence of "but", you can get the range of "but" and trim the original string down
NSString * test = [NSString stringWithString:#"iphone is good but rest of string"];
NSRange range = [test rangeOfString:#"but"];
if (range.length > 0) {
NSString *adjusted = [test substringToIndex:range.location];
NSLog(#"result %#", adjusted);
}
EDIT
We can assume that the search does not want to cut of "butter is yellow", and can change the range to include " but"
NSRange range = [test rangeOfString:#" but"];
Try this:-
NSArray *array = [string componentsSeperatedBy:#"good"];
NSString *requiredString = [array objectAtIndex:0];
NSArray *array = [string componentsSeparatedByString:stringToSearch];
NSString *requiredString;
if ([array count] > 0) {
requiredString = [[array objectAtIndex:0] stringByAppendingString:stringToSearch];
}
If I have formatting for a textfield like:
//Formats the textfield based on the pickers.
- (void)pickerView:(UIPickerView *)pickerView didSelectRow:(NSInteger)row inComponent:(NSInteger)component {
NSString *result = [feetArray objectAtIndex:[feetPicker selectedRowInComponent:0]];
result = [result stringByAppendingFormat:#"%#ft", [feetArray objectAtIndex:[feetPicker selectedRowInComponent:1]]];
result = [result stringByAppendingFormat:#" %#", [inchArray objectAtIndex:[inchesPicker selectedRowInComponent:0]]];
result = [result stringByAppendingFormat:#"%#", [inchArray objectAtIndex:[inchesPicker selectedRowInComponent:1]]];
result = [result stringByAppendingFormat:#" %#in", [fractionArray objectAtIndex:[fractionPicker selectedRowInComponent:0]]];
myTextField.text = result;
}
Which display's in the textfield like 00ft 00 0/16in How can I change that all to inches with decimal? I'll need to take the ft, and multiply by 12 = variable.Then add that to inches, as well as take my fraction 1/16 and divide that by 16 to get my decimal value and then add that to the inches so it shows like 1234.0625 in order to make my calculation. Can someone help me accomplish this? Thank you in advance!
NSString * theString = RiseTextField.text;
NSString * feetString = [theString substringWithRange:NSMakeRange(0, 2)];
NSString * inchesString = [theString substringWithRange:NSMakeRange(5, 2)];
NSUInteger rangeLength = ([theString length] == 14) ? 1 : 2;
NSString * fractionString = [theString substringWithRange:NSMakeRange(8, rangeLength)];
double totalInInches = [feetString doubleValue] * 12 + [inchesString doubleValue] + [fractionString doubleValue] / 16;
You can easily get the number that you want by doing the calculations with the numbers you have there. Once you've got the actual number, you should use a NSNumberFormatter to present it with the desired amount of decimals and format.
This should solve your problem. Or did you need help converting the strings to numbers so that you can add them together?