Dev NotesSwiftWorking with String

Working with String

Operations on String in Swift

DevSwiftData Structures & Algorithms

Introduction

Working with String in Swift can be tricky sometimes, some simple operations like getting character at a specific index could be seemingly over complicated, but actually having the right mental model and knowledge could make it straightforward.

This note is to provide some usecases on how to work with String in Swift, and hopefully it would be helpful for you to understand how it works under the hood.

Loop through a String

with characters

let string = "Hello, world!"
 
for char in string {
  // where char is a `Character`
  print(char)
}

with indices

let string = "Hello, world!"
 
for i in string.indices {
  // where i is a `String.Index`
  print(string[i])
}

Make a Substring from a String

Substring is a great feature in Swift, it allows us to take a subsequence from a string without copying the underlying data, which makes it a lot more efficient.

Here are some examples on how to make a Substring from a String:

let string = "Hello, world!"
// Inferred as `Substring`
let substring = string[string.startIndex..<string.endIndex]
// or using startIndex and endIndex directly to indicate the range of the whole string
// Inferred as `String.SubSequence` as it's from generic `Sequence`
let substringFromStartIndex = string[string.startIndex...]
let substringToEndIndex = string[..<string.endIndex]
// or using three dots to implicitly having the range of the whole string
// Inferred as `String.SubSequence` as it's from generic `Sequence`
let substring = string[...]

Example: Simple Fuzzy Matching

There is a great example on objc.io about how to use Substring to implement a simple fuzzy matching algorithm.

S01E211-simple-fuzzy-matching by objc.io
extension String {
    func fuzzyMatch(_ needle: String) -> Bool {
        if needle.isEmpty { return true }
        var remainder = needle[...]
        for char in self {
            if char == remainder[remainder.startIndex] {
                remainder.removeFirst()
                if remainder.isEmpty { return true }
            }
        }
        return false
    }
}

It’s a perfect fit for solving this Leetcode problem: 392. Is Subsequence

Remove first character from a Substring

In the above example, we have used removeFirst() to remove the first character from a Substring.

let string = "Hello, world!"
// If you want to create a new `Substring` directly with dropFirst(_ k: Int), you can use the following syntax:
var substring = string.dropFirst()
 
// If you want to work with the original string, you can use the following syntax, and handle the character at the startIndex manually:
var substring2 = string[...]
substring2.removeFirst()

To be noted, removeFirst() will mutate the string and trigger copy-on-write semantics.