156 votes

Utilisez une chaîne dynamique (variable) comme motif de regex en JavaScript

Je veux ajouter une balise (variable) aux valeurs avec une regex, le motif fonctionne bien avec PHP mais j'ai des problèmes pour l'implémenter en JavaScript.

Le motif est (value est la variable) :

/(?!(?:[^<]+>|[^>]+<\/a>))\b(value)\b/is

J'ai échappé les barres obliques inverses :

var str = $("#div").html();
var regex = "/(?!(?:[^<]+>|[^>]+<\\/a>))\\b(" + value + ")\\b/is";
$("#div").html(str.replace(regex, "

0 votes

Est-ce que valeur est une variable?

275voto

acdcjunior Points 19898

Pour créer l'expression régulière à partir d'une chaîne, vous devez utiliser l'objet RegExp de JavaScript.

Si vous souhaitez également faire correspondre/remplacer plus d'une fois, alors vous devez ajouter le drapeau g (correspondance globale). Voici un exemple :

var stringToGoIntoTheRegex = "abc";
var regex = new RegExp("#" + stringToGoIntoTheRegex + "#", "g");
// à ce stade, la ligne ci-dessus est la même que : var regex = /#abc#/g;

var input = "Bonjour c'est #abc# un peu #abc# de contenu.";
var output = input.replace(regex, "!!");
alert(output); // Bonjour c'est !! un peu !! de contenu.

Démo JSFiddle ici.

Dans le cas général, échappez la chaîne avant de l'utiliser en tant qu'expression régulière :

Toute chaîne n'est pas une expression régulière valide, pourtant : il existe certains caractères spéciaux, comme ( ou [. Pour contourner ce problème, il suffit d'échapper la chaîne avant de la transformer en une expression régulière. Une fonction utilitaire pour cela se trouve dans l'exemple ci-dessous :

function escapeRegExp(stringToGoIntoTheRegex) {
    return stringToGoIntoTheRegex.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&');
}

var stringToGoIntoTheRegex = escapeRegExp("abc"); // c'est le seul changement par rapport ci-dessus
var regex = new RegExp("#" + stringToGoIntoTheRegex + "#", "g");
// à ce stade, la ligne ci-dessus est la même que : var regex = /#abc#/g;

var input = "Bonjour c'est #abc# un peu #abc# de contenu.";
var output = input.replace(regex, "!!");
alert(output); // Bonjour c'est !! un peu !! de contenu.

Démo JSFiddle ici.


Note : l'expression régulière dans la question utilise le modifieur s, qui n'existait pas au moment de la question, mais existe aujourd'hui -- un drapeau/modifieur s (dotall) en JavaScript.

2 votes

C'est génial et le meilleur exemple que j'ai trouvé jusqu'à présent sur l'utilisation d'une variable dynamique dans une expression régulière, merci!

1 votes

Pour 2019 il y a s modifieur, voir de nouveau le lien MDN dans la note de la réponse.

0 votes

Let idr = new RegExp(variable + "$"); Table.find({ field: new RegExp(idr, 'i') }) J'ai fait comme ça. Cheers.

19voto

happytime harry Points 1602

Si vous essayez d'utiliser une valeur de variable dans l'expression, vous devez utiliser le RegExp "constructor".

var regex = "(?!(?:[^<]+>|[^>]+<\/a>))\b(" + value + ")\b";
new RegExp(regex, "is")

11voto

will Points 85

J'ai trouvé que je devais doubler le caractère oblique \\b pour que cela fonctionne. Par exemple, pour supprimer les mots "1x" d'une chaîne de caractères en utilisant une variable, j'avais besoin d'utiliser :

    str = "1x";
    var regex = new RegExp("\\b"+str+"\\b","g"); // same as inv.replace(/\b1x\b/g, "")
    inv=inv.replace(regex, "");

9voto

Halcyon Points 31203

Vous n'avez pas besoin des " pour définir une expression régulière, donc simplement :

var regex = /(?!(?:[^<]+>|[^>]+<\/a>))\b(value)\b/is; // ceci est une syntaxe valide

Si value est une variable et que vous souhaitez une expression régulière dynamique, alors vous ne pouvez pas utiliser cette notation ; utilisez la notation alternative.

String.replace accepte également des chaînes de caractères en entrée, donc vous pouvez faire "fox".replace("fox", "bear");

Alternative:

var regex = new RegExp("/(?!(?:[^<]+>|[^>]+<\/a>))\b(value)\b/", "is");
var regex = new RegExp("/(?!(?:[^<]+>|[^>]+<\/a>))\b(" + value + ")\b/", "is");
var regex = new RegExp("/(?!(?:[^<]+>|[^>]+<\/a>))\b(.*?)\b/", "is");

Gardez à l'esprit que si value contient des caractères d'expressions régulières comme (, [ et ?, vous devrez les échapper.

5 votes

La première option ne fonctionnerait pas à moins de chercher la chaîne "value"

0 votes

@happytimeharry Il semble y avoir un conflit entre les deux regexps qu'il a postés.

0 votes

@Fritz van Campen il semble que l'intention du motif, étant donné l'exemple de son javascript, était d'utiliser une variable

4voto

JRD Points 83

J'ai trouvé ce fil de discussion utile - donc j'ai pensé ajouter la réponse à mon propre problème.

Je voulais modifier un fichier de configuration de base de données (datastax cassandra) à partir d'une application node en javascript et pour l'un des paramètres du fichier j'avais besoin de faire correspondre une chaîne de caractères puis de remplacer la ligne suivante.

Voici ma solution.

dse_cassandra_yaml='/etc/dse/cassandra/cassandra.yaml'

// a) trouver la chaîne de recherche et récupérer tout le texte sur la ligne suivante
// b) remplacer tout le texte de la ligne suivante par une nouvelle chaîne fournie à la fonction
// note - ne modifie pas la chaîne de recherche 
function replaceStringNextLine(file, searchString, newString) {
fs.readFile(file, 'utf-8', function(err, data){
if (err) throw err;
    // besoin d'utiliser un double échappement '\\' lors de la mise de regex dans les chaînes !
    var re = "\\s+(\\-\\s(.*)?)(?:\\s|$)";
    var myRegExp = new RegExp(searchString + re, "g");
    var match = myRegExp.exec(data);
    var replaceThis = match[1];
    var writeString = data.replace(replaceThis, newString);
    fs.writeFile(file, writeString, 'utf-8', function (err) {
    if (err) throw err;
        console.log(file + ' mis à jour');
    });
});
}

searchString = "data_file_directories:"
newString = "- /mnt/cassandra/data"

replaceStringNextLine(dse_cassandra_yaml, searchString, newString );

Après exécution, cela changera le paramètre du répertoire de données existant par le nouveau :

Fichier de configuration avant:

data_file_directories:  
   - /var/lib/cassandra/data

Fichier de configuration après:

data_file_directories:  
- /mnt/cassandra/data

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X