web-dev-qa-db-ja.com

Javascript Regexpループのすべての一致

スタックオーバーフローのリッチテキストエディターで同様のことをしようとしています。このテキストを考えます:

[Text Example][1]

[1][http://www.example.com]

見つかった各[string][int]をループしたいので、次のようにします。

var Text = "[Text Example][1]\n[1][http: //www.example.com]";
// Find resource links
var arrMatch = null;
var rePattern = new RegExp(
  "\\[(.+?)\\]\\[([0-9]+)\\]",
  "gi"
);
while (arrMatch = rePattern.exec(Text)) {
  console.log("ok");
}

これはうまく機能し、[string][int]ごとに「OK」を警告します。ただし、必要なのは、見つかった一致ごとに、最初の一致を2番目の一致のコンポーネントに置き換えることです。

そのため、ループでは$ 2は最初に一致したint部分を表し、この正規表現(pseduo)を実行します

while (arrMatch = rePattern.exec(Text)) {
    var FindIndex = $2; // This would be 1 in our example
    new RegExp("\\[" + FindIndex + "\\]\\[(.+?)\\]", "g")

    // Replace original match now with hyperlink
}

これは一致します

[1][http://www.example.com]

最初の例の最終結果は次のとおりです。

<a href="http://www.example.com" rel="nofollow">Text Example</a>

編集

私はこれまでのところこれを得ました:

var Text = "[Text Example][1]\n[1][http: //www.example.com]";
// Find resource links
reg = new RegExp(
  "\\[(.+?)\\]\\[([0-9]+)\\]",
  "gi");
var result;
while ((result = reg.exec(Text)) !== null) {
  var LinkText = result[1];
  var Match = result[0];
  Text = Text.replace(new RegExp(Match, "g"), '<a href="#">" + LinkText + "</a>');
}
console.log(Text);
37
Tom Gullen

私はこれで最終的にそれをやることができました:

var Text = "[Text Example][1]\n[1][http: //www.example.com]";
// Find resource links
reg = new RegExp(
  "\\[(.+?)\\]\\[([0-9]+)\\]",
  "gi");
var result;
while (result = reg.exec(Text)) {
  var LinkText = result[1];
  var Match = result[0];
  var LinkID = result[2];
  var FoundURL = new RegExp("\\[" + LinkID + "\\]\\[(.+?)\\]", "g").exec(Text);
  Text = Text.replace(Match, '<a href="' + FoundURL[1] + '" rel="nofollow">' + LinkText + '</a>');
}
console.log(Text);
33
Tom Gullen

Jasonには、既存のMarkdownライブラリを使用する方が高速/安全であることに同意しますが、あなたは String.prototype.replace を探しています(また、RegExpリテラルを使用してください!):

var Text = "[Text Example][1]\n[1][http: //www.example.com]";
var rePattern = /\[(.+?)\]\[([0-9]+)\]/gi;

console.log(Text.replace(rePattern, function(match, text, urlId) {
  // return an appropriately-formatted link
  return `<a href="${urlId}">${text}</a>`;
}));
37
s4y

ここではexecメソッドを使用しています。これは、すべての一致を取得し(while whileループを使用)、一致した文字列の位置を取得するのに役立ちます。

    var input = "A 3 numbers in 333";
    var regExp = /\b(\d+)\b/g, match;
    while (match = regExp.exec(input))
      console.log("Found", match[1], "at", match.index);
    // → Found 3 at 2 //   Found 333 at 15 
4
Vasyl Gutnyk

Execと一致の微妙さに依存せずにすべての一致を反復処理する別の方法は、最初のパラメーターとして正規表現を使用し、2番目のパラメーターとして関数を使用する文字列置換関数を使用することです。このように使用すると、関数の引数は最初のパラメーターとして一致全体を受け取り、グループ化された一致を次のパラメーターとして受け取り、インデックスを最後のパラメーターとして受け取ります。

var text = "[Text Example][1]\n[1][http: //www.example.com]";
// Find resource links
var arrMatch = null;
var rePattern = new RegExp("\\[(.+?)\\]\\[([0-9]+)\\]", "gi");
text.replace(rePattern, function(match, g1, g2, index){
    // Do whatever
})

グローバルJS変数argumentsを使用して、最初と最後のグループを除いて、各一致のすべてのグループを反復処理することもできます。

0
Mario Vázquez

以下に小さな例を示します。 \numberは、正規表現でグループ一致番号を参照するために使用され、$numberは、グループの結果を参照するために置換関数で使用されるため、テキストが

[Text Example][1]\n[1][http://www.example.com]

一致し、一致する場合

[Text Example][1]\n[2][http://www.example.com]

しません

var re = /\[(.+?)\]\[([0-9]+)\s*.*\s*\[(\2)\]\[(.+?)\]/gi;
var str = '[Text Example][1]\n[1][http://www.example.com]';
var subst = '<a href="$4">$1</a>';

var result = str.replace(re, subst);
console.log(result);
0
Ruslan López

この形式は Markdown に基づいています。 いくつかのJavaScriptポート が利用可能です。構文全体が必要ない場合は、リンクに関連する部分をstealingすることをお勧めします。

0
Jason McCreary