У меня есть эта строка:

"Test abc test test abc test test test abc test test abc"

Выполнение :

str = str.replace('abc', '');

Кажется, удаляет только первое вхождение abc в приведенной выше строке.

Как я могу заменить все его вхождения?

4280
Click Upvote 17 Июл 2009 в 21:53

29 ответов

Лучший ответ

Примечание. Не используйте этот код в критичном для производительности коде.

В качестве альтернативы регулярным выражениям для простой литеральной строки, вы можете использовать

str = "Test abc test test abc test...".split("abc").join("");

Общая картина

str.split(search).join(replacement)

Раньше в некоторых случаях это было быстрее, чем при использовании replaceAll и регулярных выражений, но в современных браузерах это больше не так.

Тест: https://jsperf.com/replace-all-vs-split-join

Вывод: если у вас есть критичный к производительности вариант использования (например, обработка сотен строк), используйте метод Regexp. Но для большинства типичных случаев лучше не беспокоиться о специальных символах.

1505
Click Upvote 13 Дек 2019 в 16:10

// зациклить, пока число вхождений не достигнет 0. ИЛИ просто скопировать / вставить

    function replaceAll(find, replace, str) 
    {
      while( str.indexOf(find) > -1)
      {
        str = str.replace(find, replace);
      }
      return str;
    }
26
Gonzalo Larralde 5 Сен 2013 в 14:01

Предыдущие ответы слишком сложны. Просто используйте функцию замены следующим образом:

str.replace(/your_regex_pattern/g, replacement_string);

Примере:

var str = "Test abc test test abc test test test abc test test abc";

var res = str.replace(/[abc]+/g, "");

console.log(res);
13
Peter Mortensen 18 Ноя 2018 в 03:27

Это самые распространенные и читаемые методы.

var str = "Test abc test test abc test test test abc test test abc"

Метод 1:

str = str.replace(/abc/g, "replaced text");

Метод 2:

str = str.split("abc").join("replaced text");

Метод 3:

str = str.replace(new RegExp("abc", "g"), "replaced text");

Метод 4:

while(str.includes("abc")){
    str = str.replace("abc", "replaced text");
}

Выход:

console.log(str);
// Test replaced text test test replaced text test test test replaced text test test replaced text
54
Peter Mortensen 8 Мар 2020 в 18:27

Вы можете просто использовать метод ниже

/**
 * Replace all the occerencess of $find by $replace in $originalString
 * @param  {originalString} input - Raw string.
 * @param  {find} input - Target key word or regex that need to be replaced.
 * @param  {replace} input - Replacement key word
 * @return {String}       Output string
 */
function replaceAll(originalString, find, replace) {
  return originalString.replace(new RegExp(find, 'g'), replace);
};
8
tk_ 23 Фев 2016 в 03:47

< EM> Update :

Уже несколько поздно для обновления, но так как я просто наткнулся на этот вопрос и заметил, что мой предыдущий ответ не тот, которым я доволен. Поскольку вопрос касался замены одного слова, невероятно, что никто не думал об использовании границ слов (\b)

'a cat is not a caterpillar'.replace(/\bcat\b/gi,'dog');
//"a dog is not a caterpillar"

Это простое регулярное выражение, которое в большинстве случаев избегает замены частей слов. Тем не менее, тире - все еще считается границей слова. Поэтому в этом случае можно использовать условные выражения, чтобы избежать замены строк, таких как cool-cat:

'a cat is not a cool-cat'.replace(/\bcat\b/gi,'dog');//wrong
//"a dog is not a cool-dog" -- nips
'a cat is not a cool-cat'.replace(/(?:\b([^-]))cat(?:\b([^-]))/gi,'$1dog$2');
//"a dog is not a cool-cat"

В основном, этот вопрос такой же, как вопрос здесь: Javascript заменяет "" "на" '""

@ Майк, проверь ответ, который я дал им ... регулярное выражение - не единственный способ заменить несколько вхождений подстроки, далеко не так. Думай гибко, думай о разделении!

var newText = "the cat looks like a cat".split('cat').join('dog');

В качестве альтернативы, чтобы предотвратить замену частей слова - что будет делать и одобренный ответ! Вы можете обойти эту проблему, используя регулярные выражения, которые, я признаю, несколько более сложны и, как следствие, тоже немного медленнее:

var regText = "the cat looks like a cat".replace(/(?:(^|[^a-z]))(([^a-z]*)(?=cat)cat)(?![a-z])/gi,"$1dog");

Вывод такой же, как принятый ответ, однако с использованием выражения / cat / g в этой строке:

var oops = 'the cat looks like a cat, not a caterpillar or coolcat'.replace(/cat/g,'dog');
//returns "the dog looks like a dog, not a dogerpillar or cooldog" ?? 

Ой, действительно, это, вероятно, не то, что вы хотите. Что же тогда? ИМХО, регулярное выражение, которое заменяет только 'условно'. (то есть не часть слова), вот так:

var caterpillar = 'the cat looks like a cat, not a caterpillar or coolcat'.replace(/(?:(^|[^a-z]))(([^a-z]*)(?=cat)cat)(?![a-z])/gi,"$1dog");
//return "the dog looks like a dog, not a caterpillar or coolcat"

Я думаю, это отвечает вашим потребностям. Конечно, это не полная защита, но этого должно быть достаточно, чтобы вы начали. Я бы порекомендовал прочитать еще на этих страницах. Это окажется полезным в совершенствовании этого выражения для удовлетворения ваших конкретных потребностей.

http://www.javascriptkit.com/jsref/regexp.shtml

http://www.regular-expressions.info


Окончательное добавление.

Учитывая, что этот вопрос по-прежнему получает много просмотров, я подумал, что мог бы добавить пример .replace, используемого с функцией обратного вызова. В этом случае это значительно упрощает выражение , а обеспечивает еще большую гибкость, например, заменяет правильную заглавную букву или заменяет cat и cats за один раз:

'Two cats are not 1 Cat! They\'re just cool-cats, you caterpillar'
   .replace(/(^|.\b)(cat)(s?\b.|$)/gi,function(all,char1,cat,char2)
    {
       //check 1st, capitalize if required
       var replacement = (cat.charAt(0) === 'C' ? 'D' : 'd') + 'og';
       if (char1 === ' ' && char2 === 's')
       {//replace plurals, too
           cat = replacement + 's';
       }
       else
       {//do not replace if dashes are matched
           cat = char1 === '-' || char2 === '-' ? cat : replacement;
       }
       return char1 + cat + char2;//return replacement string
    });
//returns:
//Two dogs are not 1 Dog! They're just cool-cats, you caterpillar
87
Community 23 Май 2017 в 11:47

Самый простой способ сделать это без использования регулярных выражений - это разделение и соединение, как показано здесь:

var str = "Test abc test test abc test test test abc test test abc";
str.split('abc').join('')
15
Peter Mortensen 8 Мар 2020 в 18:24

Если строка содержит аналогичный шаблон, как abccc, вы можете использовать это:

str.replace(/abc(\s|$)/g, "")
13
3 revs, 2 users 78% 27 Апр 2018 в 08:49

Замена одинарных кавычек:

function JavaScriptEncode(text){
    text = text.replace(/'/g,'&apos;')
    // More encode here if required

    return text;
}
32
Termininja 17 Дек 2017 в 15:53
var str = "ff ff f f a de def";
str = str.replace(/f/g,'');
alert(str);

http://jsfiddle.net/ANHR9/

13
pkdkk 4 Сен 2013 в 10:01
function replaceAll(str, find, replace) {
  var i = str.indexOf(find);
  if (i > -1){
    str = str.replace(find, replace); 
    i = i + replace.length;
    var st2 = str.substring(i);
    if(st2.indexOf(find) > -1){
      str = str.substring(0,i) + replaceAll(st2, find, replace);
    }       
  }
  return str;
}
19
Tim Rivoli 29 Сен 2014 в 19:17
str = str.replace(/abc/g, '');

В ответ на комментарий:

var find = 'abc';
var re = new RegExp(find, 'g');

str = str.replace(re, '');

В ответ на нажмите комментарий Upvote, вы можете упростить его еще больше:

function replaceAll(str, find, replace) {
  return str.replace(new RegExp(find, 'g'), replace);
}

Примечание: Регулярные выражения содержат специальные (мета) символы, и поэтому опасно слепо передавать аргумент в функции find выше без предварительной обработки для экранирования этих символов. Это описано в сети разработчиков Mozilla Руководство по JavaScript для регулярных выражений, где они представляют следующую служебную функцию (которая по крайней мере изменилась дважды, так как этот ответ был изначально написан, поэтому обязательно проверьте сайт MDN на наличие потенциальных обновлений):

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

Таким образом, чтобы сделать вышеописанную функцию replaceAll() более безопасной, ее можно изменить на следующую, если вы также включите escapeRegExp:

function replaceAll(str, find, replace) {
  return str.replace(new RegExp(escapeRegExp(find), 'g'), replace);
}
4309
Sean Bright 19 Фев 2020 в 14:29

Мне нравится этот метод (выглядит немного чище):

text = text.replace(new RegExp("cat","g"), "dog"); 
16
Peter Mortensen 27 Май 2017 в 21:57

Если вы пытаетесь гарантировать, что искомая строка не будет существовать даже после замены, вам нужно использовать цикл.

Например:

var str = 'test aabcbc';
str = str.replace(/abc/g, '');

После завершения у вас все еще будет «test abc»!

Самый простой цикл для решения этой проблемы:

var str = 'test aabcbc';
while (str != str.replace(/abc/g, '')){
   str.replace(/abc/g, '');
}

Но это запускает замену дважды для каждого цикла. Возможно (рискуя быть отвергнутым), что может быть объединено для немного более эффективной, но менее читаемой формы:

var str = 'test aabcbc';
while (str != (str = str.replace(/abc/g, ''))){}
// alert(str); alerts 'test '!

Это может быть особенно полезно при поиске дублирующихся строк.
Например, если у нас есть «a ,,, b» и мы хотим удалить все повторяющиеся запятые.
[В этом случае можно сделать .replace (/, + / g, ','), но в какой-то момент регулярное выражение становится сложным и достаточно медленным, чтобы выполнять цикл.]

10
SamGoody 28 Сен 2014 в 19:58

Если то, что вы хотите найти, уже находится в строке, и у вас нет под рукой оператора regex escaper, вы можете использовать join / split:

    function replaceMulti(haystack, needle, replacement)
    {
        return haystack.split(needle).join(replacement);
    }

    someString = 'the cat looks like a cat';
    console.log(replaceMulti(someString, 'cat', 'dog'));
21
Pitu 23 Июл 2018 в 17:42

Хотя люди упоминали об использовании регулярных выражений, но есть лучший подход, если вы хотите заменить текст независимо от случая текста. Как прописные или строчные. Используйте ниже синтаксис

//Consider below example
originalString.replace(/stringToBeReplaced/gi, '');

//Output will be all the occurrences removed irrespective of casing.

Подробный пример вы можете найти здесь.

10
evandrix 8 Июн 2016 в 18:51

Скажем, вы хотите заменить все «abc» на «x»:

let some_str = 'abc def def lom abc abc def'.split('abc').join('x')
console.log(some_str) //x def def lom x x def

Я пытался придумать что-то более простое, чем модификация прототипа строки.

40
Peter Mortensen 27 Май 2017 в 22:01
str = str.replace(new RegExp("abc", 'g'), "");

Работал лучше для меня, чем приведенные выше ответы. поэтому new RegExp("abc", 'g') создает RegExp, который соответствует всему вхождению ('g' флаг) текста ("abc"). Вторая часть - это то, что заменяется в вашем случае пустой строкой (""). str - это строка, и мы должны переопределить ее, поскольку replace(...) просто возвращает результат, но не переопределяет. В некоторых случаях вы можете использовать это.

25
csomakk 29 Дек 2017 в 17:52
str = str.replace(/abc/g, '');

Или попробуйте функцию replaceAll отсюда:

Какие полезные методы JavaScript расширяют встроенные объекты?

str = str.replaceAll('abc', ''); OR

var search = 'abc';
str = str.replaceAll(search, '');

РЕДАКТИРОВАТЬ . Разъяснение о заменеВсе наличие

Метод replaceAll добавлен в прототип String. Это означает, что он будет доступен для всех строковых объектов / литералов.

Например.

var output = "test this".replaceAll('this', 'that');  //output is 'test that'.
output = output.replaceAll('that', 'this'); //output is 'test this'
44
Community 23 Май 2017 в 12:34

Использование регулярного выражения с установленным флагом g заменит все:

someString = 'the cat looks like a cat';
anotherString = someString.replace(/cat/g, 'dog');
// anotherString now contains "the dog looks like a dog"

Смотрите здесь также

678
R3tep 17 Май 2016 в 12:15

Просто добавьте /g

document.body.innerHTML = document.body.innerHTML.replace('hello', 'hi');

Кому

// Replace 'hello' string with /hello/g regular expression.
document.body.innerHTML = document.body.innerHTML.replace(/hello/g, 'hi');

/g означает глобальный

7
Valentin 15 Окт 2015 в 12:13

Для полноты картины я подумал о том, какой метод я должен использовать для этого. Есть два основных способа сделать это, как предлагают другие ответы на этой странице.

Примечание. Как правило, расширение встроенных прототипов в JavaScript обычно не рекомендуется. Я предоставляю в качестве расширений прототипа String просто для иллюстрации, демонстрируя различные реализации гипотетического стандартного метода на встроенном прототипе String.


Реализация на основе регулярных выражений

String.prototype.replaceAll = function(search, replacement) {
    var target = this;
    return target.replace(new RegExp(search, 'g'), replacement);
};

Разделение и объединение (функциональная) реализация

String.prototype.replaceAll = function(search, replacement) {
    var target = this;
    return target.split(search).join(replacement);
};

Не зная слишком много о том, как регулярные выражения работают за кулисами с точки зрения эффективности, я склонялся к расколу и присоединялся к реализации в прошлом, не задумываясь о производительности. Когда я задумался о том, что является более эффективным, и по какой причине я использовал это в качестве предлога, чтобы выяснить это.

На моей машине с Chrome Windows 8 реализация на основе регулярных выражений является самой быстрой , а реализация разбиения и объединения на 53% медленнее . Это означает, что регулярные выражения в два раза быстрее для ввода lorem ipsum, который я использовал.

Проверьте это тест , где эти две реализации работают друг против друга.


Как отмечается в комментарии ниже @ThomasLeduc и других, может быть проблема с реализацией на основе регулярных выражений, если search содержит определенные символы, которые зарезервированы как специальные символы в регулярных выражениях. Реализация предполагает, что вызывающая сторона будет избегать строки заранее или будет передавать только те строки, которые не содержат символов в таблице, в Регулярные выражения (MDN).

MDN также предоставляет реализацию, позволяющую избежать наших строк. Было бы хорошо, если бы это было также стандартизировано как RegExp.escape(str), но, увы, его не существует:

function escapeRegExp(str) {
  return str.replace(/[.*+?^${}()|[\]\\]/g, "\\$&"); // $& means the whole matched string
}

Мы могли бы вызвать escapeRegExp в нашей реализации String.prototype.replaceAll, однако я не уверен, насколько это повлияет на производительность (потенциально даже для строк, для которых экранирование не требуется, как для всех буквенно-цифровых строк).

2430
Peter Mortensen 27 Май 2017 в 21:55

Это самая быстрая версия, в которой не используются регулярные выражения .

Пересмотренный jsperf

replaceAll = function(string, omit, place, prevstring) {
  if (prevstring && string === prevstring)
    return string;
  prevstring = string.replace(omit, place);
  return replaceAll(prevstring, omit, place, string)
}

Это почти в два раза быстрее, чем метод split и join.

Как указано в комментарии, это не будет работать, если ваша переменная omit содержит place, как в replaceAll("string", "s", "ss"), потому что она всегда сможет заменить другое вхождение слова.

В моей рекурсивной замене есть еще один jsperf с вариантами, которые идут еще быстрее (http: // jsperf.com/replace-all-vs-split-join/12 ) !

  • Обновление от 27 июля 2017 года. Похоже, что RegExp теперь имеет самую быструю производительность в недавно выпущенном Chrome 59.
25
Cole Lawrence 27 Июл 2017 в 15:57

Использование RegExp в JavaScript может сделать эту работу за вас, просто сделайте что-то вроде приведенного ниже кода, не забывайте /g, после которого выделяется global :

var str ="Test abc test test abc test test test abc test test abc";
str = str.replace(/abc/g, '');

Если вы думаете о повторном использовании, создайте функцию, которая сделает это за вас, но это не рекомендуется, поскольку это всего лишь одна строчная функция, но, опять же, если вы интенсивно ее используете, вы можете написать что-то вроде этого:

String.prototype.replaceAll = String.prototype.replaceAll || function(string, replaced) {
  return this.replace(new RegExp(string, 'g'), replaced);
};

И просто используйте его в своем коде снова и снова, как показано ниже:

var str ="Test abc test test abc test test test abc test test abc";
str = str.replaceAll('abc', '');

Но, как я упоминал ранее, это не будет иметь большого значения с точки зрения написания строк или производительности, только кэширование функции может повлиять на более высокую производительность на длинных строках, а также на хорошую практику DRY-кода, если вы хотите использовать повторно.

41
Alireza 12 Окт 2019 в 05:18

Используйте регулярное выражение:

str.replace(/abc/g, '');
37
Peter Mortensen 27 Май 2017 в 21:56

Вот функция-прототип строки, основанная на принятом ответе:

String.prototype.replaceAll = function (find, replace) {
    var str = this;
    return str.replace(new RegExp(find, 'g'), replace);
};

< Сильный > ИЗМЕНИТЬ

Если ваш find будет содержать специальные символы, вам нужно их экранировать:

String.prototype.replaceAll = function (find, replace) {
    var str = this;
    return str.replace(new RegExp(find.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&'), 'g'), replace);
};

Скрипка: http://jsfiddle.net/cdbzL/

108
jesal 7 Окт 2013 в 16:40

Для замены разового использования:

var res = str.replace('abc', "");

Для замены несколько раз используйте:

var res = str.replace(/abc/g, "");
59
Mihai Chelaru 29 Май 2019 в 12:33
while (str.indexOf('abc') !== -1)
{
    str = str.replace('abc', '');
}
13
zdennis 29 Апр 2014 в 10:25

Сопоставить с глобальным регулярным выражением:

anotherString = someString.replace(/cat/g, 'dog');
65
scronide 6 Май 2009 в 23:23
1144783