2017-04-05 8 views
8

swiftでコードを更新しています。3. RangeをNSRangeに変換する際にエラーが発生しました。迅速な3でそれを行う方法?NSRangeの範囲を変換する方法は?

func nsRange(_ range : Range<String.Index>) -> NSRange { 
    let utf16from = String.UTF16View.Index(range.lowerBound, within: utf16) 
    let utf16to = String.UTF16View.Index(range.upperBound, within: utf16) 
    return NSRange(location: utf16.startIndex.distanceTo(utf16from), length: utf16from.distanceTo(utf16to)) 
} 
+0

http://stackoverflow.com/a/30404532/1187415チェック変換スウィフト1.2、2のための方法、および3 –

+0

を持って...とスウィフト4 –

答えて

28

Xcodeの9•スウィフト4

extension StringProtocol where Index == String.Index { 
    func nsRange(from range: Range<Index>) -> NSRange { 
     return NSRange(range, in: self) 
    } 
} 

let string = "Hello USA !!! Hello World !!!" 

if let range = string.range(of: "Hello World") { 
    let nsRange = string.nsRange(from: range) 
    (string as NSString).substring(with: nsRange) // "Hello World" 
} 

ます。また、対応するnsRangeを作成することができます(以下のようStringProtocolを拡張:)方法の:

extension StringProtocol where Index == String.Index { 
    func nsRange<T: StringProtocol>(of string: T, options: String.CompareOptions = [], range: Range<Index>? = nil, locale: Locale? = nil) -> NSRange? { 
     guard let range = self.range(of: string, options: options, range: range ?? startIndex..<endIndex, locale: locale ?? .current) else { return nil } 
     return NSRange(range, in: self) 
    } 
    func nsRanges<T: StringProtocol>(of string: T, options: String.CompareOptions = [], range: Range<Index>? = nil, locale: Locale? = nil) -> [NSRange] { 
     var start = range?.lowerBound ?? startIndex 
     let end = range?.upperBound ?? endIndex 
     var ranges: [NSRange] = [] 
     while start < end, let range = self.range(of: string, options: options, range: start..<end, locale: locale ?? .current) { 
      ranges.append(NSRange(range, in: self)) 
      start = range.upperBound 
     } 
     return ranges 
    } 
} 

let string = "Hello USA !!! Hello World !!!" 

if let nsRange = string.nsRange(of: "Hello World") { 
    (string as NSString).substring(with: nsRange) // "Hello World" 
} 
let nsRanges = string.nsRanges(of: "Hello") 
print(nsRanges) // "[{0, 5}, {19, 5}]\n" 
+0

のために迅速な3コードが間違っているとします。https: //developer.apple.com/documentation/swift/string.utf16view – apinho

1

私は

(私はすでに彼の評判を高め)スウィフト3.のための彼のソリューションを使用するが、私は専門的な拡張を提供するであろういくつかの時間前に、この項目の執筆者に大きな感謝を述べたいと思いまず第一にレンジ自体

スウィフト4

extension Range where Bound == String.Index { 
    var nsRange:NSRange { 
     return NSRange(location: self.lowerBound.encodedOffset, 
         length: self.upperBound.encodedOffset - 
           self.lowerBound.encodedOffset) 
    } 
} 

ため、この場合には、前のサンプルでは、​​

012のように見えるかもしれません
let string = "Hello USA !!! Hello World !!!" 

if let nsrange = string.range(of: "Hello World")?.nsRange { 
    (string as NSString).substring(with: nsrange) // "Hello World" 
} 
+1

Swift 4は、 'Range 'から 'NSRange'を作成するネイティブな方法を紹介しています。 – vadian

+0

レオはStringインスタンスを必要とするNSRange(range、in:self)を提供していますが、RangeをNSRangeに変換する必要がある場合はどうしたらよいでしょうか。 String.Indexがプロトコル 'FixedWidthInteger'に準拠していないため、NSRange.init(Range )が機能しません –

関連する問題