I am trying to remove a character in the middle of a string.
This is what I would like to do
let index = 4 let str = "abcdefg" let strRemoved = str.remove(at: index) //Removes only character at pos 4 print(strRemoved) //prints 'abcdfg' You can't. String collection's index it is not an Int but you can implement your own remove(at:) method that takes an Int as argument. Note that to remove an element from your collection you would need to declare it as variable:
extension StringProtocol where Self: RangeReplaceableCollection { @discardableResult mutating func remove(at offset: Int) -> Element? { guard let index = index(startIndex, offsetBy: offset, limitedBy: endIndex) else { return nil } return remove(at: index) } } Playground testing:
let index = 4 var abc = "abcdefg" if let removedChar = abc.remove(at: index) { // Removes at pos 4 print(removedChar) // prints 'e' print(abc) // prints 'abcdfg' } Let's look at how you'd remove a character from the middle of String by looking at an example use case where we remove random letters from a string until it is empty.
Method 1: Use String.remove(at:) to remove characters
Here we use the method String.remove(at:) to select the character to remove. Unfortunately, Strings aren't indexed with Int, so you need to provide a String.Index value:
var str = "abcdefg" while str.count > 0 { let randomIndex = Int.random(in: 0 ..< str.count) str.remove(at: str.index(str.startIndex, offsetBy: randomIndex)) print(str) } Output:
abdefg bdefg befg bfg bf f
Method 2: Use prefix() and dropFirst() to construct a new String
Alternatively, you could use prefix() and dropFirst() to select parts of your original String to construct a new String. Both of these methods return type Substring, so it is necessary to call String() after concatenating the parts:
var str = "abcdefg" while str.count > 0 { let randomIndex = Int.random(in: 0 ..< str.count) str = String(str.prefix(randomIndex) + str.dropFirst(randomIndex + 1)) print(str) } Output:
abcdeg abcde acde acd cd c
Method 3: Turn str into [Character]
If you're going to repeatedly add, remove, and change characters, consider turning your String into an [Character]. That is much easier to work with, because [Character] can be indexed with Int, and you can easily turn an [Character] called chars back into a String with String(chars).
var str = "abcdefg" var chars = Array(str) while chars.count > 0 { let randomIndex = Int.random(in: 0 ..< chars.count) chars.remove(at: randomIndex) print(String(chars)) } Output:
acdefg acefg aceg aeg ae a
var str = "abcdefg"thenlet strRemoved = str.remove(at: str.index(str.startIndex, offsetBy: 4))