web-dev-qa-db-fra.com

Comment utilisez-vous une variable dans une expression régulière?

Je voudrais créer une méthode String.replaceAll() en JavaScript et je pense qu'utiliser une expression régulière serait la façon la plus fastidieuse de le faire. Cependant, je n'arrive pas à comprendre comment passer une variable à un regex. Je peux déjà le faire, ce qui remplacera toutes les instances de "B" par "A".

"ABABAB".replace(/B/g, "A");

Mais je veux faire quelque chose comme ça:

String.prototype.replaceAll = function(replaceThis, withThis) {
    this.replace(/replaceThis/g, withThis);
};

Mais évidemment, cela ne remplacera que le texte "replaceThis"... alors comment puis-je passer cette variable dans ma chaîne de regex?

1202
JC Grubbs

Au lieu d'utiliser la syntaxe /regex/g, vous pouvez créer un nouvel objet RegExp :

var replace = "regex";
var re = new RegExp(replace,"g");

Vous pouvez créer dynamiquement des objets regex de cette façon. Ensuite, vous ferez:

"mystring".replace(re, "newstring");
1652
Eric Wendelin

Comme Eric Wendelin l'a mentionné, vous pouvez faire quelque chose comme ceci:

str1 = "pattern"
var re = new RegExp(str1, "g");
"pattern matching .".replace(re, "regex");

Cela donne "regex matching .". Cependant, cela échouera si str1 est ".". Vous vous attendriez à ce que le résultat soit "pattern matching regex", en remplaçant le point par "regex", mais cela se révélera être ...

regexregexregexregexregexregexregexregexregexregexregexregexregexregexregexregexregexregex

En effet, bien que "." soit une chaîne, dans le constructeur RegExp, elle est toujours interprétée comme une expression régulière, c'est-à-dire tout caractère ne comprenant pas de saut de ligne, c'est-à-dire chaque caractère de la chaîne. À cette fin, la fonction suivante peut être utile:

 RegExp.quote = function(str) {
     return str.replace(/([.?*+^$[\]\\(){}|-])/g, "\\$1");
 };

Ensuite, vous pouvez faire:

str1 = "."
var re = new RegExp(RegExp.quote(str1), "g");
"pattern matching .".replace(re, "regex");

donnant "pattern matching regex".

195
Gracenotes

"ABABAB".replace(/B/g, "A");

Comme toujours: n'utilisez pas regex sauf si vous devez le faire. Pour une chaîne simple remplacer, l'idiome est:

'ABABAB'.split('B').join('A')

Dans ce cas, vous n'avez pas à vous soucier des problèmes de citation mentionnés dans la réponse de Gracenotes.

106
bobince

Pour ceux qui cherchent à utiliser variable avec la méthode match, cela a fonctionné pour moi

var alpha = 'fig';
'food fight'.match(alpha + 'ht')[0]; // fight
33
Steven Penny

Cette:

var txt=new RegExp(pattern,attributes);

est équivalent à ceci:

var txt=/pattern/attributes;

Voir http://www.w3schools.com/jsref/jsref_obj_regexp.asp .

29
Jeremy Ruten

Si vous voulez obtenir TOUTES les occurrences (g), soyez insensible à la casse (i) et utilisez des limites pour que ce ne soit pas un mot contenu dans un autre mot (\\b):

re = new RegExp(`\\b${replaceThis}\\b`, 'gi');

Exemple:

let inputString = "I'm John, or johnny, but I prefer john.";
let replaceThis = "John";
let re = new RegExp(`\\b${replaceThis}\\b`, 'gi');
console.log(inputString.replace(re, "Jack")); // I'm Jack, or johnny, but I prefer Jack.
24
JBallin
this.replace( new RegExp( replaceThis, 'g' ), withThis );
19
tvanfosson

Vous voulez construire l’expression régulière de manière dynamique et pour cela, la solution appropriée consiste à utiliser le constructeur new RegExp(string). Pour que le constructeur traite les caractères spéciaux littéralement , vous devez les échapper. Il existe une fonction intégrée dans widget de saisie semi-automatique de l'interface utilisateur jQuery appelée $.ui.autocomplete.escapeRegex:

[...] vous pouvez utiliser la fonction intégrée $.ui.autocomplete.escapeRegex. Cela prend un seul argument de chaîne et échappe à tous les caractères regex, ce qui rend le résultat sûr à passer à new RegExp().

Si vous utilisez l'interface utilisateur jQuery, vous pouvez utiliser cette fonction ou copier sa définition à partir de la source :

function escapeRegex( value ) {
    return value.replace( /[\-\[\]{}()*+?.,\\\^$|#\s]/g, "\\$&" );
}

Et utilisez-le comme ceci:

"[z-a][z-a][z-a]".replace(new RegExp(escapeRegex("[z-a]"), "g"), "[a-z]");
//            escapeRegex("[z-a]")       -> "\[z\-a\]"
// new RegExp(escapeRegex("[z-a]"), "g") -> /\[z\-a\]/g
// end result                            -> "[a-z][a-z][a-z]"
10
Salman A
String.prototype.replaceAll = function (replaceThis, withThis) {
   var re = new RegExp(replaceThis,"g"); 
   return this.replace(re, withThis);
};
var aa = "abab54..aba".replaceAll("\\.", "v");

Testez avec ceci outil

9
unigogo
String.prototype.replaceAll = function(a, b) {
    return this.replace(new RegExp(a.replace(/([.?*+^$[\]\\(){}|-])/ig, "\\$1"), 'ig'), b)
}

Testez le comme:

var whatever = 'Some [b]random[/b] text in a [b]sentence.[/b]'

console.log(whatever.replaceAll("[", "<").replaceAll("]", ">"))
5
MetalGodwin

Voici une autre implémentation de replaceAll:

    String.prototype.replaceAll = function (stringToFind, stringToReplace) {
        if ( stringToFind == stringToReplace) return this;
        var temp = this;
        var index = temp.indexOf(stringToFind);
        while (index != -1) {
            temp = temp.replace(stringToFind, stringToReplace);
            index = temp.indexOf(stringToFind);
        }
        return temp;
    };
4
scripto

Bien que vous puissiez créer des RegExp créés de manière dynamique (comme pour les autres réponses à cette question), je vais faire écho à mon commentaire tiré d'un message similaire : La forme fonctionnelle de String.replace () est extrêmement utile et réduit souvent le besoin d’objets RegExp créés dynamiquement. (ce qui est un peu pénible car vous devez exprimer l'entrée du constructeur RegExp sous forme de chaîne plutôt que d'utiliser les barres obliques/[A-Z] +/format littéral regexp)

3
Jason S

Et la version coffeescript de la réponse de Steven Penny, puisqu'il s'agit du résultat n ° 2 de Google .... même si café ne contient que du javascript avec beaucoup de caractères supprimés ...;)

baz = "foo"
filter = new RegExp(baz + "d")
"food fight".match(filter)[0] // food

et dans mon cas particulier

robot.name=hubot
filter = new RegExp(robot.name)
if msg.match.input.match(filter)
  console.log "True!"
3
keen

Pour satisfaire mon besoin d'insérer une variable/alias/fonction dans une expression régulière, voici ce que j'ai proposé:

oldre = /xx\(""\)/;
function newre(e){
    return RegExp(e.toString().replace(/\//g,"").replace(/xx/g, yy), "g")
};

String.prototype.replaceAll = this.replace(newre(oldre), "withThis");

où "oldre" est l'expression rationnelle d'origine dans laquelle je veux insérer une variable, "xx" est l'espace réservé pour cette variable/alias/fonction et "yy" le nom, l'alias ou la fonction de la variable.

3
Alex Li

Vous pouvez toujours utiliser indexOf à plusieurs reprises:

String.prototype.replaceAll = function(substring, replacement) {
    var result = '';
    var lastIndex = 0;

    while(true) {
        var index = this.indexOf(substring, lastIndex);
        if(index === -1) break;
        result += this.substring(lastIndex, index) + replacement;
        lastIndex = index + substring.length;
    }

    return result + this.substring(lastIndex);
};

Cela ne va pas dans une boucle infinie lorsque le remplacement contient la correspondance.

1
Ry-

Votre solution est ici:

Passez une variable à une expression régulière.

Celui que j'ai implémenté est en prenant la valeur d'un champ de texte que vous souhaitez remplacer et un autre, le champ de texte "Remplacer par", en récupérant la valeur d'un champ de texte dans une variable et en définissant la variable sur RegExp. fonction pour remplacer davantage. Dans mon cas, j'utilise Jquery, vous pouvez aussi le faire en JavaScript uniquement.

Code JavaScript:

  var replace =document.getElementById("replace}"); // getting a value from a text field with I want to replace
  var replace_with = document.getElementById("with"); //Getting the value from another text fields with which I want to replace another string.

  var sRegExInput = new RegExp(replace, "g");    
  $("body").children().each(function() {
    $(this).html($(this).html().replace(sRegExInput,replace_with));
  });

Ce code est sur l'événement Onclick d'un bouton, vous pouvez le mettre dans une fonction à appeler.

Alors maintenant, vous pouvez passer variable dans la fonction de remplacement.

1
Ajit Hogade

Vous pouvez l'utiliser si $ 1 ne fonctionne pas avec vous

var pattern = new RegExp("amman","i");
"abc Amman efg".replace(pattern,"<b>"+"abc Amman efg".match(pattern)[0]+"</b>");
1
Fareed Alnamrouti

Aucune de ces réponses n'était claire pour moi. J'ai finalement trouvé une bonne explication sur http://burnignorance.com/php-programming-tips/how-to-use-a-variable-in-replace-function-of-javascript/

La réponse simple est:

var search_term = new RegExp(search_term, "g");    
text = text.replace(search_term, replace_term);

Par exemple:

$("button").click(function() {
  Find_and_replace("Lorem", "Chocolate");
  Find_and_replace("ipsum", "ice-cream");
});

function Find_and_replace(search_term, replace_term) {
  text = $("textbox").html();
  var search_term = new RegExp(search_term, "g");
  text = text.replace(search_term, replace_term);
  $("textbox").html(text);
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<textbox>
  Lorem ipsum Lorem ipsum Lorem ipsum Lorem ipsum Lorem ipsum Lorem ipsum
</textbox>
<button>Click me</button>
0
Paul Jones