Substitua vários caracteres em uma chamada de substituição

257

Pequena pergunta muito simples, mas não entendo bem como fazê-lo.

Preciso substituir todas as instâncias de '_' por um espaço e todas as instâncias de '#' por nada / vazio.

var string = '#Please send_an_information_pack_to_the_following_address:';

Eu tentei isso:

string.replace('#','').replace('_', ' ');

Eu realmente não gosto de encadear comandos como este. Existe outra maneira de fazer isso em um?

Shannon Hochkins
fonte
Veja a resposta a esta pergunta: stackoverflow.com/questions/7072330/…
DeweyOx

Respostas:

515

Use o operador OR ( |):

var str = '#this #is__ __#a test###__';
str.replace(/#|_/g,''); // result: "this is a test"

Você também pode usar uma classe de personagem:

str.replace(/[#_]/g,'');

Violino

Se você deseja substituir o hash por uma coisa e o sublinhado por outra, será necessário encadear. No entanto, você pode adicionar um protótipo:

String.prototype.allReplace = function(obj) {
    var retStr = this;
    for (var x in obj) {
        retStr = retStr.replace(new RegExp(x, 'g'), obj[x]);
    }
    return retStr;
};

console.log('aabbaabbcc'.allReplace({'a': 'h', 'b': 'o'}));
// console.log 'hhoohhoocc';

Por que não cadeia, no entanto? Não vejo nada de errado nisso.

tckmn
fonte
Isso é legal, mas preciso substituir sublinhados por espaços não vazios, posso fazer isso?
Shannon Hochkins
Pensava assim, mas ainda assim você me ajudou a entender como substituir expressões trabalhar um pouco melhor :)
Shannon Hochkins
Seu protótipo não funciona? você é capaz de fornecer um exemplo no violino, eu continuo recebendo erros
Shannon Hochkins
3
Outra opção para #|_é [#_], e assim como você pode usar +para coincidir com quaisquer jogos consecutivos para melhorar o desempenho
Ian
3
Legal obrigado ... se necessário, substitua espaços em branco e outros símbolos str.replace(/[+ -]/g,'');apenas coloque espaço em branco no meio.
Equiman 5/05
53

Encadeamento é legal, por que descartá-lo?

Enfim, aqui está outra opção em uma substituição:

string.replace(/#|_/g,function(match) {return (match=="#")?"":" ";})

A substituição escolherá "" se corresponder == "#", "" se não.

[Atualização] Para uma solução mais genérica, você pode armazenar suas seqüências de substituição em um objeto:

var replaceChars={ "#":"" , "_":" " };
string.replace(/#|_/g,function(match) {return replaceChars[match];})
Christophe
fonte
4
dê o passo extra: var regex = new RegExp( Object.keys(replaceChars).join("|"), "g"); string.replace(regex,function(match) {return replaceChars[match];})isso facilita a modificação dos replaceChars.
RozzA 04/08/19
@RozzA thanks. Object.keys não era mainstream no momento.
Christophe
Eu esqueci completamente opção função de substituição de cerca de substituir segundo parâmetro, por me ajudar a lembrar :)
Luckylooke
48

Se você deseja substituir vários caracteres, pode chamar o String.prototype.replace()argumento de substituição, sendo uma função que é chamada para cada correspondência. Tudo o que você precisa é de um objeto que represente o mapeamento de caracteres que você usará nessa função.

Por exemplo, se você quiser asubstituir por x, bpor ye ccom z, poderá fazer algo assim:

var chars = {'a':'x','b':'y','c':'z'};
var s = '234abc567bbbbac';
s = s.replace(/[abc]/g, m => chars[m]);
console.log(s);

Saída :234xyz567yyyyxz

Voicu
fonte
3
desde que você use o ES6 (função de seta), você também deve substituir varpor constaqui. uma alternativa para suporte estendido ao navegador:var s ='234abc567bbbbac'; s = s.replace(/[abc]/g, function(m) { return {'a':'x','b':'y','c':'z'}[m]; }); console.log(s);
Felix Geenen 23/03
1
@FelixGeenen 1. você mata a portabilidade 2. se optar por redefinir caracteres ou s, você receberá um erro de tempo de execução, o que acaba com sua 'robustez', 3. não há garantia de proteger s contra mutações e religiões que não sejam puramente ideológicas. É uma coisa maravilhosa ver que esse trecho ainda funcionará no windows98 recém-instalado no clique duplo / cscript / wscript:var chars = {a:'1', b:'2', c:'3'}; var s = '123abc123'; var u = s.replace(/[abc]/g, function(m) { return chars[m]; }); WScript.echo(u);
Dmitry
isto é muito bom. obrigado. Qual é a parte em que você usou um objeto para fazer uma declaração ou. você tem documentação ou referência a algo que explica isso? Muito bom caso de uso.
Christian Matthew
39

Especifique o /gsinalizador (global) na expressão regular para substituir todas as correspondências em vez da primeira:

string.replace(/_/g, ' ').replace(/#/g, '')

Para substituir um caractere por uma coisa e um caractere diferente por outra, você não pode realmente precisar de duas chamadas separadas replace. Você pode abstraí-lo para uma função como a Maçaneta da porta, embora eu provavelmente desejaria que ele pegasse um objeto antigo / novo como pares chave / valor em vez de uma matriz plana.

Mark Reed
fonte
como incluiria o hash também?
Shannon Hochkins
4

Você também pode tentar o seguinte:

function replaceStr(str, find, replace) {
    for (var i = 0; i < find.length; i++) {
        str = str.replace(new RegExp(find[i], 'gi'), replace[i]);
    }
    return str;
}

var text = "#here_is_the_one#";
var find = ["#","_"];
var replace = ['',' '];
text = replaceStr(text, find, replace);
console.log(text);

findrefere-se ao texto a ser encontrado e replaceao texto a ser substituído por

Isso substituirá caracteres que não diferenciam maiúsculas de minúsculas. Para fazer o contrário, altere os sinalizadores Regex conforme necessário. Por exemplo: para caso sensível, substitua:

new RegExp(find[i], 'g')
Tapan Bala
fonte
4

Você pode apenas tentar o seguinte:

str.replace(/[.#]/g, 'replacechar');

isso substituirá., - e # pelo seu substitechar!

karim somai
fonte
Esta resposta já foi fornecida e não lida com a substituição de caracteres diferentes por outros, consulte OP.
Shannon Hochkins
3

Aqui está uma maneira simples de fazer isso sem o RegEx.
Você pode criar protótipos e / ou armazenar em cache as coisas conforme desejado.

// Example: translate( 'faded', 'abcdef', '123456' ) returns '61454'
function translate( s, sFrom, sTo ){
    for ( var out = '', i = 0; i < s.length; i++ ){
        out += sTo.charAt( sFrom.indexOf( s.charAt(i) ));
    }
    return out;
}
Beejor
fonte
Eu sei que você não indicou, mas não é muito mais elegante usar apenas regex? str.replace(/#|_/g,'')
Shannon Hochkins
1
@ ShannonHochkins Com certeza! Não pretendo me basear no RegEx; Estou apenas mostrando outra opção. O RegEx nem sempre é intuitivo e se presta a ser usado "como um martelo, tratando todos os problemas como um prego". Além disso, olhando para as outras respostas, como uma função reutilizável, essa não é muito mais longa e os parâmetros são fáceis de entender. Pessoalmente, eu faria um pequeno RegEx para a pergunta aqui, e faz sentido se você está apenas procurando um trecho rápido de apresentação que você não se importa de não entender completamente.
Beejor
Bem, se você precisar traduzir um caractere (à la sed y command ou à Unix tr), esta parece ser a resposta certa.
Édouard
3

Tente por favor:

  • substituir várias cordas

    var str = "http://www.abc.xyz.com"; str = str.replace(/http:|www|.com/g, ''); //str is "//.abc.xyz"

  • substituir vários caracteres

    var str = "a.b.c.d,e,f,g,h"; str = str.replace(/[.,]/g, ''); //str is "abcdefgh";

Boa sorte!

Tran Hung
fonte
2

Você também pode passar um objeto RegExp para o método de substituição, como

var regexUnderscore = new RegExp("_", "g"); //indicates global match
var regexHash = new RegExp("#", "g");

string.replace(regexHash, "").replace(regexUnderscore, " ");

Javascript RegExp

Michael Sanchez
fonte
O OP não deseja encadear replacechamadas - isso não ajuda a evitar isso.
Dennis
2

yourstring = '#Envie send_an_information_pack_to_the_following_address:';

substitua '#' por '' e substitua '_' por um espaço

var newstring1 = yourstring.split('#').join('');
var newstring2 = newstring1.split('_').join(' ');

newstring2 é o seu resultado

Hafsul Maru
fonte
Sua resposta não usa um fragmento de jQuery e também não segue o OP, '#this #is__ #a test ### ' .split ('_'). Join ('') não funcionaria como você iria acabar com mais espaços em branco
Shannon Hochkins
@ ShannonHochkins Como mais espaços em branco serão adicionados?
Hafsul Maru
Dê uma olhada no meu exemplo, quando houver um sublinhado antes de um espaço, ou dois sublinhados, você terá vários espaços.
Shannon Hochkins
@ShannonHochkins, o interlocutor lida com a sequência '#Por favor, envie uma informação_pacote_para_a_fazer o seguinte endereço:'; não há espaço aqui. Por que eu vou pensar nisso. quando pensar, por que apenas sobre o espaço, muitas outras coisas podem acontecer.
Hafsul Maru 23/01
Eu sugiro que você leia o OP, eu sou o pôster original e você pode ver claramente na minha primeira variável var str = '#this #is__ __#a test###__';que há claramente vários espaços nessa string.
Shannon Hochkins
2

Aqui está outra versão usando o String Prototype. Aproveitar!

String.prototype.replaceAll = function(obj) {
    let finalString = '';
    let word = this;
    for (let each of word){
        for (const o in obj){
            const value = obj[o];
            if (each == o){
                each = value;
            }
        }
        finalString += each;
    }

    return finalString;
};

'abc'.replaceAll({'a':'x', 'b':'y'}); //"xyc"
Diego Fortes
fonte
1

Não sei se isso ajudará, mas eu queria remover <b>e</b> da minha string

então eu usei

mystring.replace('<b>',' ').replace('</b>','');

Então, basicamente, se você deseja que um número limitado de caracteres seja reduzido e não perca tempo, isso será útil.

Hrishikesh Kale
fonte
-1

Aqui está uma função "HTML seguro" usando uma função de substituição múltipla 'reduzir' (essa função aplica cada substituição a toda a cadeia de caracteres, portanto, as dependências entre substituições são significativas).

// Test:
document.write(SafeHTML('<div>\n\
    x</div>'));

function SafeHTML(str)
    {
    const replacements = [
        {'&':'&amp;'},
        {'<':'&lt;'},
        {'>':'&gt;'},
        {'"':'&quot;'},
        {"'":'&apos;'},
        {'`':'&grave;'},
        {'\n':'<br>'},
        {' ':'&nbsp;'}
        ];
    return replaceManyStr(replacements,str);
    } // HTMLToSafeHTML

function replaceManyStr(replacements,str)
    {
    return replacements.reduce((accum,t) => accum.replace(new RegExp(Object.keys(t)[0],'g'),t[Object.keys(t)[0]]),str);
    }
David Spector
fonte
Graças ao cargo, no entanto, é bastante extensa em comparação com a resposta aceita
Shannon Hochkins
A resposta para a pergunta é uma função de uma linha. Como isso é "extenso"? Tornar a entrada do usuário segura é um exemplo importante. Você é muito crítico. 'reduzir' é uma técnica muito útil que você deve conhecer.
David Spector
Eu disse que sua resposta é muito extensa, é muito mais código, você está usando expressões regulares de qualquer maneira, apenas tornando o processo muito complicado, sem saber como você acha que sua resposta é uma redução em comparação com qualquer uma dessas respostas ...
Shannon Hochkins 9/09/19
Minha resposta é uma resposta 'reduzida' porque ela usa a função Array.prototype.reduce. Uma resposta mais curta pode usar uma sequência em vez de chaves de propriedade, explorando o fato de que uma função "HTML seguro" funciona apenas na substituição de caracteres únicos. Eu desafio você a encontrar uma resposta mais elegante em vez de reclamar rudemente em público como este.
David Spector
Na verdade, eu agradeci, e fiz críticas, você aceitou e decidiu escrever algo sarcástico, se vamos começar com métodos funcionais para executar, em vez de métodos encadeados prototípicos como deveríamos ser, algo muito mais simples como: jsfiddle .net / shannonhochkins / xsm9j610 / 21
Shannon Hochkins