Swift 4:如何统计字符串数组元素在字符串/字符串数组中的出现次数?
看起来你正在做一个很有意思的圣经数据统计项目!我来帮你解决名字统计的问题,分步骤来:
第一步:先整理你的名字数组
你的names数组当前是按换行分割,但原字符串里其实是空格分隔的,可能会产生空字符串,先处理成干净的数组:
let nameString = """ Abigail Ada Ahlai Angel Anna """ // 按空白(空格+换行)分割,过滤空字符串,得到干净的名字数组 let names = nameString.components(separatedBy: .whitespacesAndNewlines) .filter { !$0.isEmpty } // 如果需要忽略大小写匹配(比如经文里的"abigail"也要统计),可以提前转成小写的Set(Set查询效率更高) let lowercasedNameSet = Set(names.map { $0.lowercased() })
第二步:统计单个字符串中的名字出现次数
要准确统计,最好用正则匹配完整单词,避免把"Anna"误匹配到"Annabelle"这种部分重合的词里。这里写一个可复用的函数:
import Foundation // 正则需要依赖Foundation框架 func countNameOccurrences(in text: String, names: [String], caseInsensitive: Bool = true) -> [String: Int] { var counts: [String: Int] = [:] let processedText = caseInsensitive ? text.lowercased() : text for name in names { let targetName = caseInsensitive ? name.lowercased() : name // 转义名字里的特殊字符(比如如果名字包含.或者?),然后用\b匹配单词边界 let regexPattern = "\\b\(NSRegularExpression.escapedPattern(for: targetName))\\b" guard let regex = try? NSRegularExpression(pattern: regexPattern) else { counts[name] = 0 continue } // 统计当前名字的匹配次数 let matchCount = regex.numberOfMatches( in: processedText, range: NSRange(processedText.startIndex..., in: processedText) ) counts[name] = matchCount } return counts }
第三步:统计字符串数组(所有经文)中的名字出现次数
你需要一个全局计数器,遍历所有verse的文本,累加每个名字的出现次数。结合你的现有代码修改如下:
// 初始化全局统计字典,记录每个名字的总出现次数 var totalNameCounts: [String: Int] = [:] for chapter in genesis!.chapters { for verse in chapter.verses { // 从verse字典中提取经文文本(你的verse是["1":"经文内容"]结构,取第一个值即可) guard let verseText = verse.values.first else { continue // 如果没有文本就跳过当前verse } // 统计当前经文里的名字次数 let currentVerseCounts = countNameOccurrences(in: verseText, names: names) // 累加到全局统计字典 for (name, count) in currentVerseCounts { totalNameCounts[name] = (totalNameCounts[name] ?? 0) + count } } } // 最后可以按出现次数从高到低排序,拿到提及最多的名字 let sortedNameCounts = totalNameCounts.sorted { $0.value > $1.value } if let topName = sortedNameCounts.first { print("提及最多的名字:\(topName.key),共出现\(topName.value)次") }
额外优化点
- 预编译正则表达式:如果名字数量很多,每次循环创建正则会影响效率,可以提前把所有名字的正则编译好,存在字典里复用。
- 处理名字变体:圣经里有些名字可能有不同拼写(比如"Abraham"和"Abram"),如果需要合并统计,可以额外维护一个别名映射字典。
- 批量统计:如果想一次性处理所有经文文本,可以先把所有verse的文本收集成数组,再调用批量统计的函数。
内容的提问来源于stack exchange,提问作者wowmystiik
相关产品推荐
相关产品推荐

