Как заменить n-й символ строки на другой

Как я могу заменить n-й символ строки на другой?

func replace(myString:String, index:Int, newCharac:Character) -> String {
// Write correct code here
return modifiedString
}

Например, replace("House", 2, "r") должен быть равен "Horse".

Ответ 1

Подробнее см. ответ NateCook

func replace(myString: String, _ index: Int, _ newChar: Character) -> String {
    var chars = Array(myString.characters)     // gets an array of characters
    chars[index] = newChar
    let modifiedString = String(chars)
    return modifiedString
}

replace("House", 2, "r")

Это уже не актуально и устарело.

Вы всегда можете использовать swift String с NSString. Таким образом, вы можете вызвать функцию NSString в swift String. По старому stringByReplacingCharactersInRange: вы можете сделать это

var st :String = "House"
let abc = st.bridgeToObjectiveC().stringByReplacingCharactersInRange(NSMakeRange(2,1), withString:"r") //Will give Horse

Ответ 2

Решения, использующие методы NSString, не будут работать для любых строк с многобайтовыми символами Unicode. Вот два родных способа решения проблемы:

Вы можете использовать тот факт, что String является последовательностью Character, чтобы преобразовать строку в массив, изменить ее и преобразовать массив обратно:

func replace(myString: String, _ index: Int, _ newChar: Character) -> String {
    var chars = Array(myString.characters)     // gets an array of characters
    chars[index] = newChar
    let modifiedString = String(chars)
    return modifiedString
}

replace("House", 2, "r")
// Horse

С другой стороны, вы можете самостоятельно пройти через строку:

func replace(myString: String, _ index: Int, _ newChar: Character) -> String {
    var modifiedString = String()
    for (i, char) in myString.characters.enumerate() {
        modifiedString += String((i == index) ? newChar : char)
    }
    return modifiedString
}

Поскольку они полностью находятся в Swift, они оба безопасны для Unicode:

replace("🏠🏡🏠🏡🏠", 2, "🐴")
// 🏠🏡🐴🏡🏠

Ответ 3

В Swift 4 это намного проще.

let newString = oldString.prefix(n) + char + oldString.dropFirst(n + 1)

Это пример:

let oldString = "Hello, playground"
let newString = oldString.prefix(4) + "0" + oldString.dropFirst(5)

где результат

Hell0, playground

Тип newString - подстрока. Оба prefix и dropFirst возвращают Substring. Подстрока - это фрагмент строки, другими словами, подстроки бывают быстрыми, потому что вам не нужно выделять память для содержимого строки, но используется то же место для хранения, что и исходная строка.

Ответ 4

Я нашел это решение.

var string = "Cars"
let index = string.index(string.startIndex, offsetBy: 2)
string.replaceSubrange(index...index, with: "t")
print(string)
// Cats

Ответ 5

Я расширил ответ нейта Кука и превратил его в расширение строки.

extension String {

    //Enables replacement of the character at a specified position within a string
    func replace(_ index: Int, _ newChar: Character) -> String {
        var chars = Array(characters)
        chars[index] = newChar
        let modifiedString = String(chars)
        return modifiedString
    }
}

использование:

let source = "House"
let result = source.replace(2,"r")

результат "Лошадь"

Ответ 6

После просмотра Swift Docs мне удалось выполнить эту функцию:

//Main function
func replace(myString:String, index:Int, newCharac:Character) -> String {
    //Looping through the characters in myString
    var i = 0
    for character in myString {
        //Checking to see if the index of the character is the one we're looking for
        if i == index {
            //Found it! Now instead of adding it, add newCharac!
            modifiedString += newCharac
        } else {
            modifiedString += character
        }
        i = i + 1
    }
    // Write correct code here
    return modifiedString
}

Обратите внимание, что это не проверено, но оно должно дать вам правильную идею.

Ответ 7

func replace(myString:String, index:Int, newCharac:Character) -> String {

    var modifiedString = myString
    let range = Range<String.Index>(
        start: advance(myString.startIndex, index),
        end: advance(myString.startIndex, index + 1))
    modifiedString.replaceRange(range, with: "\(newCharac)")
    return modifiedString
}

Я бы предпочел передать String, чем a Character.

Ответ 8

Я думаю, что то, что @Greg пытался достичь с его расширением, заключается в следующем:

mutating func replace(characterAt index: Int, with newChar: Character) {
    var chars = Array(characters)
    if index >= 0 && index < self.characters.count {
        chars[index] = newChar
        let modifiedString = String(chars)
        self = modifiedString
    } else {
        print("can't replace character, its' index out of range!")
    }
}

использование:

let source = "House"
source.replace(characterAt: 2, with: "r") //gives you "Horse"

Ответ 9

Строки в swift не имеют доступа для чтения или записи одного символа. Там отличное сообщение блога Оле Бегеманна, описывающее, как строки в быстрой работе.

Примечание: приведенная ниже реализация неверна, прочитайте добавление

Итак, правильный путь - это взять левую часть строки до символа index -1, добавить заменяющий символ, а затем добавить строку из индекса + 1 до конца:

func myReplace(myString:String, index:Int, newCharac:Character) -> String {
    var modifiedString: String

    let len = countElements(myString)

    if (index < len) && (index >= 0) {
        modifiedString = myString.substringToIndex(index) + newCharac + myString.substringFromIndex(index + 1)
    } else {
        modifiedString = myString
    }

    return modifiedString
}

Примечание: в моей реализации я решил вернуть исходную строку, если индекс не находится в допустимом диапазоне

Добавление Благодаря @slazyk, который узнал, что моя реализация неверна (см. комментарий), я предоставляю новую быструю версию этой функции.

func replace(myString:String, index:Int, newCharac:Character) -> String {
    var modifiedString: String

    if (index < 0) || (index >= countElements(myString)) {
        modifiedString = myString
    } else {
        var start = myString.startIndex
        var end = advance(start, index)

        modifiedString = myString[start ..< end]
        modifiedString += newCharac

        start = end.successor()
        end = myString.endIndex

        modifiedString += myString[start ... end]
    }

    return modifiedString
}

@codester ответ выглядит очень хорошо, и это, вероятно, то, что я буду использовать сам. Было бы интересно узнать, как сравниваются действия, используя, с одной стороны, полностью быстрое решение и переключение на objective-c.

Ответ 10

Вот эффективный ответ:

import Foundation
func replace(myString:String, index:Int, newCharac:Character) -> String {
return myString.substringToIndex(index-1) + newCharac + myString.substringFromIndex(index)
}