2017-10-21 13 views
0

スイフト3導入String.range(of:options)。次に、この機能により、可能な一致は、例えば、NSRegularExpressionオブジェクトを作成せずに文字列の一部である:NSRegularExpressionを使用しないと、文字列正規表現のすべての一致を取得するにはどうすればよいですか?

let text = "it is need #match my both #hashtag!" 
let match = text.range(of: "(?:^#|\\s#)[\\p{L}0-9_]*", options: .regularExpression)! 

print(text[match]) // #math 

しかし、可能な一致が正規表現の両方の出現である(すなわち、#match#hashtagある)、代わりに最初の?

+0

https://stackoverflow.com/questions/32305891/index-of-a-substring-in-a-string-with-swift/323​​06142#32306142あなたが実装する必要がありますあなた自身。方法の範囲を確認する(of :)私はこれをどのように達成したか –

+0

@LeoDabus私は、拡張機能や強化機能なしで、バニラソリューションを探しています。私のケースは単純ですが、私は一つの状況でそれを使用します。でもありがとう。 – Macabeus

+0

このメソッドを使用する場合は、自分で実装する以外の方法はありません。 –

答えて

1
let text = "it is need #match my both #hashtag!" 
// create an object to store the ranges found 
var ranges: [Range<String.Index>] = [] 
// create an object to store your search position 
var start = text.startIndex 
// create a while loop to find your regex ranges 
while let range = text.range(of: "(?:^#|\\s#)[\\p{L}0-9_]*", options: .regularExpression, range: start..<text.endIndex) { 
    // append your range found 
    ranges.append(range) 
    // and change the startIndex of your string search 
    start = range.lowerBound < range.upperBound ? range.upperBound : text.index(range.lowerBound, offsetBy: 1, limitedBy: text.endIndex) ?? text.endIndex 
} 
ranges.forEach({print(text[$0])}) 

これは、あなたのコード内で複数回、それを使用する必要がある場合は、あなたのプロジェクトに、この拡張機能を追加する必要があります

#match

#hashtag

を出力します:

extension String { 
    func ranges(of string: String, options: CompareOptions = .literal) -> [Range<Index>] { 
     var result: [Range<Index>] = [] 
     var start = startIndex 
     while let range = range(of: string, options: options, range: start..<endIndex) { 
      result.append(range) 
      start = range.lowerBound < range.upperBound ? range.upperBound : index(range.lowerBound, offsetBy: 1, limitedBy: endIndex) ?? endIndex 
     } 
     return result 
    } 
} 

用法:

let text = "it is need #match my both #hashtag!" 
let pattern = "(?:^#|\\s#)[\\p{L}0-9_]*" 
let ranges = text.ranges(of: pattern, options: .regularExpression) 
let matches = ranges.map{text[$0]} 
print(matches) // [" #match", " #hashtag"] 
+0

ありがとうございます!私は本当になぜデフォルトライブラリがこの便利な機能を持っていないのか理解できません。それは 'range'を持っていますが、' ranges'はありません。 – Macabeus

+1

ようこそ。少なくとも私たちは必要に応じて言語を変更できます。範囲の拡張子をプロジェクトに投稿したリンクから追加し、必要に応じて使用することができます –

+0

これはどのように正規表現マッチングを行うのですか?私はこれがどう機能するかは分かりません。 – seaturtle

関連する問題