A Better RegularExpression

As promised a while ago I’ve sat down and hammered out a better replacement for Swift’s NSRegularExpression class. As I said then, NSRegularExpression is not actually a Swift class but rather an Objective-C class that has been bridged over to Swift via Swift’s excellent ability to interface with C, C++, and Objective-C libraries directly. But as such it has quite a few artifacts for it being an Objective-C class to begin with. For starters the integer values it is using to denote the start and end index within the string is assuming that the string is encoded as UTF-16 in memory just like Objective-C’s NSString and NSMutableString and Swift Strings are, themselves, encoding agnostic. This causes you to have to do conversions between the UTF-16 based NSRange and the encoding agnostic Range<String.Index> which, honestly, rubs up against my OCD nerve.

You can get the Swift Package here: https://github.com/GalenRhodes/RegularExpression

I have some API Documentation here: http://galenrhodes.com/RegularExpression/

Sample test code:

//
//  RegularExpressionTests.swift
//  RegularExpressionTests
//
//  Created by Galen Rhodes on 2/11/21.
//

import XCTest
@testable import RegularExpression

class RegularExpressionTests: XCTestCase {

    override func setUpWithError() throws {}

    override func tearDownWithError() throws {}

    func testRegularExpression() throws {
        let str = "Now is the time for all good men to come to the aid of their country."

        if let rx = RegularExpression(pattern: "\\b(\\S+)") {
            rx.forEachMatchString(in: str) { s in
                if let str = s[1] { print("> \"\(str)\"") }
                return false
            }
        }
        else {
            XCTFail("Malformed Regular Expression Pattern.")
        }
    }

}

And the output would be:

> "Now"
> "is"
> "the"
> "time"
> "for"
> "all"
> "good"
> "men"
> "to"
> "come"
> "to"
> "the"
> "aid"
> "of"
> "their"
> "country."

Leave a Reply