scan
こういうことに使いたい。基本的なパターンは次のとおりです。
s.scan(/\w+/)
これにより、単語文字のすべての連続したシーケンスの配列が得られます。
>> "@Identifier('VariableA', 'VariableB', 'VariableX', 'VariableZ')".scan(/\w+/)
=> ["Identifier", "VariableA", "VariableB", "VariableX", "VariableZ"]
あなたはあなたがそれらを取り巻く任意のものであなたのパターンの複数のインスタンスを持っているかもしれないと言います。あなたはネストされたsでそれを扱うことができますscan
:
s.scan(/@(\w+)\(([^)]+?)\)/).map { |m| [ m.first, m.last.scan(/\w+/) ] }
これにより、配列の配列が得られます。各内部配列には、最初の要素として「識別子」部分があり、2番目の要素の配列として「変数」部分があります。例えば:
>> s = "pancakes @Identifier('VariableA', 'VariableB', 'VariableX', 'VariableZ') pancakes @Pancakes('one','two','three') eggs"
>> s.scan(/@(\w+)\(([^)]+?)\)/).map { |m| [ m.first, m.last.scan(/\w+/) ] }
=> [["Identifier", ["VariableA", "VariableB", "VariableX", "VariableZ"]], ["Pancakes", ["one", "two", "three"]]]
「変数」ビット内でエスケープされた引用符に直面している可能性がある場合は、より複雑なものが必要になります。
式に関するいくつかの注意:
@ # A literal "@".
( # Open a group
\w+ # One more more ("+") word characters ("\w").
) # Close the group.
\( # A literal "(", parentheses are used for group so we escape it.
( # Open a group.
[ # Open a character class.
^) # The "^" at the beginning of a [] means "not", the ")" isn't escaped because it doesn't have any special meaning inside a character class.
] # Close a character class.
+? # One more of the preceding pattern but don't be greedy.
) # Close the group.
\) # A literal ")".
[^)]+?
ここでは実際には必要ありませんが、必要なだけ[^)]+
ですが、通常はそれが意味するので、欲張りでない形式を習慣的に使用します。@Identifier
グループ化は、とパーツを分離するために使用されるVariable
ため、目的のネストされた配列出力を簡単に取得できます。