Swift中字符串中子字符串的出现次数

Rez*_*eza 43 regex swift

我的主要字符串是"hello Swift Swift and Swift",substring是Swift.我需要获得在提到的字符串中出现子串"Swift"的次数.

此代码可以确定模式是否存在.

var string = "hello Swift Swift and Swift"

if string.rangeOfString("Swift") != nil {
    println("exists")
}
Run Code Online (Sandbox Code Playgroud)

现在我需要知道发生的次数.

das*_*ght 84

一种简单的方法是拆分"Swift",并从零件数量中减去1:

let s = "hello Swift Swift and Swift"
let tok =  s.components(separatedBy:"Swift")
print(tok.count-1)
Run Code Online (Sandbox Code Playgroud)

此代码打印3.

编辑:Swift 3语法之前,代码看起来像这样:

let tok =  s.componentsSeparatedByString("Swift")
Run Code Online (Sandbox Code Playgroud)

  • PedroSilva,这是不正确的.这是一个例子:`"Swift".componentsSeparatedByString("Swift").count`打印`2`.因此,`count-1`将打印出现次数,在这种情况下为`1`. (7认同)
  • 这个答案是如此错误,我不敢相信被标记为已接受。如果没有出现,则返回 -1 而不是 0,如果出现在字符串末尾 -> 返回低值,如果出现是一个接一个且没有分隔,则返回完全混乱的值 (4认同)
  • @psci 你在说什么?这不可能返回-1。你还没有尝试过这些,是吗? (2认同)

Jar*_*red 23

Swift 5 扩展

extension String {
    func numberOfOccurrencesOf(string: String) -> Int {
        return self.components(separatedBy:string).count - 1
    }
}
Run Code Online (Sandbox Code Playgroud)

使用示例

let string = "hello Swift Swift and Swift"
let numberOfOccurrences = string.numberOfOccurrencesOf(string: "Swift")
        
// numberOfOccurrences = 3
Run Code Online (Sandbox Code Playgroud)


dws*_*erg 15

我建议在Swift 3中对字符串进行扩展,例如:

extension String {
    func countInstances(of stringToFind: String) -> Int {
        var stringToSearch = self
        var count = 0
        while let foundRange = stringToSearch.range(of: stringToFind, options: .diacriticInsensitive) {
            stringToSearch = stringToSearch.replacingCharacters(in: foundRange, with: "")
            count += 1
        }
        return count
    }
}
Run Code Online (Sandbox Code Playgroud)

它是一个循环,用于查找和删除stringToFind的每个实例,并在每个循环中递增计数.一旦searchString不再包含任何stringToFind,循环就会中断并返回计数.

请注意,我正在使用.diacriticInsensitive,因此它会忽略重音(例如,可以找到résume和resume).您可能希望根据要查找的字符串类型添加或更改选项.


Cœu*_*œur 14

优化dwsolbergs解决方案以更快地计算.也比快componentsSeparatedByString.

extension String {
    /// stringToFind must be at least 1 character.
    func countInstances(of stringToFind: String) -> Int {
        assert(!stringToFind.isEmpty)
        var count = 0
        var searchRange: Range<String.Index>?
        while let foundRange = range(of: stringToFind, options: [], range: searchRange) {
            count += 1
            searchRange = Range(uncheckedBounds: (lower: foundRange.upperBound, upper: endIndex))
        }
        return count
    }
}
Run Code Online (Sandbox Code Playgroud)

用法:

// return 2
"aaaa".countInstances(of: "aa")
Run Code Online (Sandbox Code Playgroud)
  • 如果你想忽略重音,你可以options: []options: .diacriticInsensitivedwsolbergs 代替.
  • 如果你想忽略大小写,你可以替换options: []options: .caseInsensitive像ConfusionTowers建议的那样.
  • 如果你想同时忽略口音和情况下,你可能会取代options: []options: [.caseInsensitive, .diacriticInsensitive]像ConfusionTowers建议.


mxc*_*xcl 11

你想要计算字符而不是子字符串:

extension String {
    func count(of needle: Character) -> Int {
        return reduce(0) {
            $1 == needle ? $0 + 1 : $0
        }
    }
}
Run Code Online (Sandbox Code Playgroud)