使用 | 找到了哪个 NSRegularExpression操作员
Which NSRegularExpression was found using the | operator
我目前正在实施 NSRegularExpressions
来检查项目中 UITextView
字符串中的模式。
模式检查和操作按预期进行;例如:我试图找到常规的 **bold**
降价模式,如果我找到它,我会应用一些归因于该范围的文本,它会按预期工作。
我遇到了一个问题。我不知道如何一次 运行 多个模式并对找到的每个模式应用不同的操作。
在我的 UITextView
委托 textViewDidChange
或 shouldChangeTextIn range: NSRange
中,我正在 运行 进行粗体模式检查 \*{2}([\w ]+)\*{2}
但我也是 运行宁斜体模式检查 \_{1}([\w ]+)\_{1}
,再次循环遍历 UITextView text
.
我实现了以下自定义函数,将传入的 regex
应用于字符串,但我必须多次调用此函数来检查每个模式,这就是为什么我想把模式检查成一个单一的,然后 "parse" 每个 match
.
fileprivate func regularExpression(regex: NSRegularExpression, type: TypeAttributes) {
let str = inputTextView.attributedText.string
let results = regex.matches(in: str, range: NSRange(str.startIndex..., in: str))
_ = results.map { self.applyAttributes(range: [=10=].range, type: type) }
}
谢谢。
编辑
我可以 "merge" 使用 |
操作数的两种模式,如下所示:
private let combinedPattern = "\*{2}([\w ]+)\*{2}|\_{1}([\w ]+)\_{1}"
但我的问题是要知道 \*{2}([\w ]+)\*{2}
或 \_{1}([\w ]+)\_{1}
找到了哪种模式
如果您使用组合模式,您会得到不同范围的匹配结果。
如果您想访问第一个捕获组(粗体模式),您需要访问 1 处的范围。当匹配匹配第二组时,您将获得第一个范围无效的范围,因此您需要检查如果不是这样有效:
results.forEach {
var range = [=10=].range(at: 1)
if range.location + range.length < str.count {
self.applyAttributes(range: range, type: .bold)
}
range = [=10=].range(at: 2)
if range.location + range.length < str.count {
self.applyAttributes(range: range, type: .italic)
}
}
之后,您可以将 TypeAttributes
枚举扩展到 return 链接到您的正则表达式的索引范围:
extension NSRange {
func isValid(for string:String) -> Bool {
return location + length < string.count
}
}
let attributes: [TypeAttributes] = [.bold, .italic]
results.forEach { match in
attributes.enumerated().forEach { index, attribute in
let range = match.range(at: index+1)
if range.isValid(for: str) {
self.applyAttributes(range: range, type: attribute[index])
}
}
}
我目前正在实施 NSRegularExpressions
来检查项目中 UITextView
字符串中的模式。
模式检查和操作按预期进行;例如:我试图找到常规的 **bold**
降价模式,如果我找到它,我会应用一些归因于该范围的文本,它会按预期工作。
我遇到了一个问题。我不知道如何一次 运行 多个模式并对找到的每个模式应用不同的操作。
在我的 UITextView
委托 textViewDidChange
或 shouldChangeTextIn range: NSRange
中,我正在 运行 进行粗体模式检查 \*{2}([\w ]+)\*{2}
但我也是 运行宁斜体模式检查 \_{1}([\w ]+)\_{1}
,再次循环遍历 UITextView text
.
我实现了以下自定义函数,将传入的 regex
应用于字符串,但我必须多次调用此函数来检查每个模式,这就是为什么我想把模式检查成一个单一的,然后 "parse" 每个 match
.
fileprivate func regularExpression(regex: NSRegularExpression, type: TypeAttributes) {
let str = inputTextView.attributedText.string
let results = regex.matches(in: str, range: NSRange(str.startIndex..., in: str))
_ = results.map { self.applyAttributes(range: [=10=].range, type: type) }
}
谢谢。
编辑
我可以 "merge" 使用 |
操作数的两种模式,如下所示:
private let combinedPattern = "\*{2}([\w ]+)\*{2}|\_{1}([\w ]+)\_{1}"
但我的问题是要知道 \*{2}([\w ]+)\*{2}
或 \_{1}([\w ]+)\_{1}
如果您使用组合模式,您会得到不同范围的匹配结果。
如果您想访问第一个捕获组(粗体模式),您需要访问 1 处的范围。当匹配匹配第二组时,您将获得第一个范围无效的范围,因此您需要检查如果不是这样有效:
results.forEach {
var range = [=10=].range(at: 1)
if range.location + range.length < str.count {
self.applyAttributes(range: range, type: .bold)
}
range = [=10=].range(at: 2)
if range.location + range.length < str.count {
self.applyAttributes(range: range, type: .italic)
}
}
之后,您可以将 TypeAttributes
枚举扩展到 return 链接到您的正则表达式的索引范围:
extension NSRange {
func isValid(for string:String) -> Bool {
return location + length < string.count
}
}
let attributes: [TypeAttributes] = [.bold, .italic]
results.forEach { match in
attributes.enumerated().forEach { index, attribute in
let range = match.range(at: index+1)
if range.isValid(for: str) {
self.applyAttributes(range: range, type: attribute[index])
}
}
}