Swift 4中Generic parameter 'Self'无法推断:String截取扩展实现求助
解决Swift String扩展中“Generic parameter 'Self' could not be inferred”错误
这个问题我之前也碰到过,核心原因是你代码里的pos是可选类型,直接和部分范围运算符..<结合时,Swift无法推断出具体的类型,所以抛出了那个错误。另外,咱们还要考虑目标字符不存在的情况,强行解包会导致崩溃,所以得把这些情况都处理好。
错误原因拆解
不管是用range(of:)还是index(of:)(Swift 4+已废弃),它们的返回值都是可选类型:
range(of:)返回Range<String.Index>?index(of:)返回String.Index?
直接写self[..<pos]时,Swift不知道这个部分范围对应的具体类型,因为pos可能是nil,自然就会报类型推断失败的错误。
正确实现方案
方案1:使用firstIndex(of:)(推荐,Swift 4+)
firstIndex(of:)是index(of:)的替代方法,更符合现代Swift API风格,实现如下:
extension String { func substringToFirstChar(of char: Character) -> String { // 用可选绑定解包可选的索引值 if let targetIndex = self.firstIndex(of: char) { return String(self[..<targetIndex]) } // 如果没找到目标字符,返回原字符串 return self } }
方案2:使用range(of:)
如果你更习惯用范围的方式处理,也可以这样写:
extension String { func substringToFirstChar(of char: Character) -> String { if let targetRange = self.range(of: String(char)) { return String(self[..<targetRange.lowerBound]) } return self } }
为什么这样能解决问题?
通过if let的可选绑定,我们把可选的索引/范围转换成了非可选值,此时..<targetIndex或..<targetRange.lowerBound的类型就明确是PartialRangeUpTo<String.Index>,Swift可以正确推断类型,错误自然就消失了。同时,我们还处理了目标字符不存在的边界情况,让方法更健壮。
内容的提问来源于stack exchange,提问作者Haiyuan
相关产品推荐
相关产品推荐

