1

I have a swift 3 string that looks like this:

var str:String = "first name: \nkevin\nlast name:\nwilliams"

when printed, it looks like this:

first name: 
kevin
last name:
williams
xxx field:
408 878 2125

I want to find the ranges of fields that start with "\n" and end with ":" so I can apply attributes to them. The field names may vary. For example, I could have "phone number:" or "address:" in other cases. how do I do this in swift 3?

an example is that I want to apply italics to the field names. so a result might be:

first name: kevin

last name: williams

xxx field: 408 878 2125

(The spaces after the colons got formatted out by stackoverflow).

mjpablo23
  • 681
  • 1
  • 7
  • 23
  • Best to try and fully explain what you want to do to begin with... Are you applying the same attributes to each "word1 word2:" line? Or are you going to remove the newline chars? Maybe show an example of how you want the end result to look? *"The field names may vary..."* Will there be 3 "field names" - or could there be 10? 20? 50? – DonMag Jun 21 '17 at 19:28
  • I've made the edits. let me know if you'd like more clarification – mjpablo23 Jun 21 '17 at 19:46

2 Answers2

1

A versatile and suitable solution is Regular Expression

let string = "first name: \nkevin\nlast name:\nwilliams"

let pattern = "\\n?(.*):"
do {
    let regex = try NSRegularExpression(pattern: pattern)
    let matches = regex.matches(in: string, range: NSRange(string.startIndex..., in: string))
    for match in matches {
        let swiftRange = Range(match.rangeAt(1), in: string)!
        print(string[swiftRange])
    }
} catch {
    print("Regex Error:", error)
}

Btw: The first entry does not start with \n

vadian
  • 274,689
  • 30
  • 353
  • 361
0

Another approach --- IF you know the format of your string will be

fieldName1: \nfieldValue1\nfieldName2: \nfieldValue2\n etc

var str:String = "first name: \nkevin\nlast name:\nwilliams\nphone:\n212.555.1212"

var charsToClear = NSMutableCharacterSet(charactersIn: ":")
charsToClear.formUnion(with: .whitespaces)

let parts = str.components(separatedBy: "\n").map{ $0.trimmingCharacters(in: charsToClear as CharacterSet) }

This will split the string into an array of alternating fieldName and fieldValue. It will also trim extra whitespace and the colons on the way. So this example string would be turned into an array containing:

[ "first name", "kevin", "last name", "williams", "phone", "212.555.1212" ]

You could then create your attributed string(s) by stepping through the array, assigning any formatting you want.

As always, implement error checking as needed.

DonMag
  • 69,424
  • 5
  • 50
  • 86