我对苹果公司的警告感到有点困惑:
'init(encodedOffset:)' is deprecated:
encodedOffset has been deprecated as most common usage is incorrect.
Use String.Index(utf16Offset:in:) to achieve the same behavior.
因为encodedOffset
和utf16Offset
不是一回事.在我的例子中,我从外部源获得字符串索引,这些索引是UTF8字节偏移量.
拿这个字符串:"👨👩👧👦"
.这是25个UTF8字节长.22个utf16字节长(苹果称之为utf16.count 11).
我从服务器收到的是{0, 25}
的范围.
以下作品:
let index = String.Index(encodedOffset: 25)
string[string.startIndex..<index] // "👨👩👧👦"
苹果公司建议将其替换为String.Index(utf16Offset:in:)
let index = String.Index(utf16Offset: 25, in: string)
string[string.startIndex..<index] // Fatal error: String index range is out of bounds
utf16Offset
应该是11,而不是25,在我得到子字符串之前,无法计算UTF8中的25个字节是11个utf16双字节,因为这取决于字符串的细节.
这也不管用
String.UTF8View.Index(utf16Offset: 25, in: string)
我如何在一个字符串中得到一个utf8字节的偏移量utf16Offset:in:
?
Swift 5: String.UTF16View.Index(encodedOffset: l) deprecated个
这个问题不是上面问题的重复,因为在那个问题中,答案是关于UTF16,而不是UTF8.
GitHub在这里发布的帖子:https://github.com/apple/swift-evolution/blob/main/proposals/0241-string-index-explicit-encoding-offset.md暗示有UTF8替代方案:
/// The UTF-8 code unit offset corresponding to this Index
public func offset<S: StringProtocol>(in utf8: S.UTF8View) -> Int { ... }
但我在其他地方找不到它.
编辑:这是让它为我工作的代码,我不确定为什么我会给那utf16Offset
个警告任何信任.
谢谢@伊泰
extension NSMutableAttributedString {
func attributedSubstring(utf8Range: NSRange) -> NSAttributedString {
let range = rangeIn(utf8Range: utf8Range)
return attributedSubstring(from: range ?? .zero)
}
func rangeIn(utf8Range range: NSRange) -> NSRange? {
let utf8 = string.utf8
guard let lowerBound = utf8.index(utf8.startIndex, offsetBy: range.location, limitedBy: utf8.endIndex)?.samePosition(in: string.utf16) else { return nil }
guard let upperBound = utf8.index(lowerBound, offsetBy: range.length, limitedBy: utf8.endIndex)?.samePosition(in: string.utf16) else { return nil }
return NSRange(lowerBound ..< upperBound, in: string)
}
}
用途:
let nsmas = NSMutableAttributedString(string: "👨👩👧👦!👩👩👦👦")
if let range = nsmas.rangeIn(utf8Range: NSMakeRange(26, 25)) {
nsmas.attributedSubstring(from: range) // "👩👩👦👦"
}
或者只是:
nsmas.attributedSubstring(utf8Range: NSMakeRange(26, 25)) // "👩👩👦👦"