Como coloco variáveis ​​dentro de strings javascript? (Node.js)

146
s = 'hello %s, how are you doing' % (my_name)

É assim que você faz em python. Como você pode fazer isso em javascript / node.js?

TIMEX
fonte
1
Tenho certeza de que era um es-lado em algum lugar strawman para fazervar s = 'hello ${my_name}, how are you doing';
Raynos
1
Eu uso como Raynos disse: const poem = "O rio negro"; const autor = "Joseph Troll"; const favePoem = `Meu poema favorito é $ {poem} por $ {author} \.`; Ou você pode usar: console.log ('% s é% d.', 'Eleven', 11);
Gilberto B. Terra Jr.

Respostas:

56

Se você quiser ter algo semelhante, poderá criar uma função:

function parse(str) {
    var args = [].slice.call(arguments, 1),
        i = 0;

    return str.replace(/%s/g, () => args[i++]);
}

Uso:

s = parse('hello %s, how are you doing', my_name);

Este é apenas um exemplo simples e não leva em consideração diferentes tipos de dados (como %ietc) ou escape de %s. Mas espero que isso lhe dê uma idéia. Tenho certeza de que também existem bibliotecas por aí que fornecem uma função como esta.

Felix Kling
fonte
1
Isso é basicamente o melhor que você obterá, pois não é suportado diretamente pela linguagem, como é em python.
Jim Schubert
A outra resposta, que apresenta util.format (), deve ser a resposta aceita ... embora de preferência também mencione as strings de modelo do ES6 (que reconhecidamente não existiam em 2011). Nós realmente devemos ser capazes de seqüestrar wiki com perguntas antigas para mantê-las atualizadas. : \
Kyle Baker
1
@FelixKling, como você é a resposta aceita, você pode atualizar sua própria resposta para apontar os outros usos corretos?
Kyle Baker
1
Isso é bom, os literais de modelo não são exatamente mesma coisa
thevangelist
Eu tive um problema ao usar "argumentos". Quando vários clientes passaram da análise, o "str" ​​foi misturado. Alguma explicação?
tspentzas
405

Com o Node.js v4, você pode usar as strings de modelo do ES6

var my_name = 'John';
var s = `hello ${my_name}, how are you doing`;
console.log(s); // prints hello John, how are you doing

Você precisa enrolar a corda dentro do backtick em ` vez de'

Sridhar
fonte
1
Mais 1 Como estamos em 2017 e o ES6 é basicamente padrão no mundo dos nós.
Jankapunkt #
1
Esta é agora (2017) a resposta correta. Esteja ciente de que você precisará do Babel em sua cadeia de ferramentas para suportar navegadores mais antigos.
superluminary
3
Sugeri aos desenvolvedores do node.js. que seria realmente útil deixar claro em páginas como nodejs.org/api/readline.html que é um backtick. Houve um problema aqui: github.com/nodejs/docs/issues/55
Gail Foad
Caiu para o backticks armadilha mim, obrigado pelo comentário;)
Overdrivr
3
E se minha string fizer parte do arquivo de configuração hello ${my_name}, how are you doinge eu desejar atribuir variáveis ​​dinamicamente após a leitura da string no config?
Amreesh Tyagi
43

A partir node.js >4.0disso, fica mais compatível com o padrão ES6, onde a manipulação de strings melhorou bastante.

A resposta para a pergunta original pode ser tão simples quanto:

var s = `hello ${my_name}, how are you doing`;
// note: tilt ` instead of single quote '

Onde a string pode espalhar várias linhas, ela facilita bastante os modelos ou processos HTML / XML. Mais detalhes e mais capacidade sobre isso: Os literais de modelo são literais de string em mozilla.org.

Andrew_1510
fonte
3
"inclinar` em vez de aspas simples '" você salvar May Day :)
Mario Binder
40

util.format faz isso.

Ele fará parte da v0.5.3 e pode ser usado assim:

var uri = util.format('http%s://%s%s', 
      (useSSL?'s':''), apiBase, path||'/');
Jim Schubert
fonte
3
Bom, obrigado pela dica! console.log ('% s', valor) também deve funcionar.
Azat
14

Faça isso:

s = 'hello ' + my_name + ', how are you doing'

Atualizar

Com o ES6, você também pode fazer isso:

s = `hello ${my_name}, how are you doing`
Merianos Nikos
fonte
O que você quer dizer com "Não é possível"? :? Se você gosta de formatar o texto, pode fazê-lo como descrito acima por Felix Kling. Esta é a melhor resposta que eu vejo aqui;) :)
Merianos Nikos
@TIMEX É possível apenas experimentá-lo.
dev_khan
5

Algumas maneiras de estender String.prototypeou usar literais de modelo do ES2015 .

var result = document.querySelector('#result');
// -----------------------------------------------------------------------------------
// Classic
String.prototype.format = String.prototype.format ||
  function () {
    var args = Array.prototype.slice.call(arguments);
    var replacer = function (a){return args[a.substr(1)-1];};
    return this.replace(/(\$\d+)/gm, replacer)
};
result.textContent = 
  'hello $1, $2'.format('[world]', '[how are you?]');

// ES2015#1
'use strict'
String.prototype.format2 = String.prototype.format2 ||
  function(...merge) { return this.replace(/\$\d+/g, r => merge[r.slice(1)-1]); };
result.textContent += '\nHi there $1, $2'.format2('[sir]', '[I\'m fine, thnx]');

// ES2015#2: template literal
var merge = ['[good]', '[know]'];
result.textContent += `\nOk, ${merge[0]} to ${merge[1]}`;
<pre id="result"></pre>

KooiInc
fonte
3

Se você estiver usando node.js, console.log () utilizará a sequência de formato como o primeiro parâmetro:

 console.log('count: %d', count);
Andrey Sidorov
fonte
Este é um bom ponto, mas a pergunta é sobre interpolação de strings. console.log()envia somente a string formatada para STDOUT. Em outras palavras, você não pode usar o resultado decount: %d
Jim Schubert
3

const format = (...args) => args.shift().replace(/%([jsd])/g, x => x === '%j' ? JSON.stringify(args.shift()) : args.shift())

const name = 'Csaba'
const formatted = format('Hi %s, today is %s and your data is %j', name, Date(), {data: {country: 'Hungary', city: 'Budapest'}})

console.log(formatted)

cstuncsik
fonte
3

Eu escrevi uma função que resolve o problema com precisão.

O primeiro argumento é a string que queria ser parametrizada. Você deve colocar suas variáveis ​​nessa string como este formato "% s1,% s2, ...% s12" .

Outros argumentos são os parâmetros respectivamente para essa sequência.

/***
 * @example parameterizedString("my name is %s1 and surname is %s2", "John", "Doe");
 * @return "my name is John and surname is Doe"
 *
 * @firstArgument {String} like "my name is %s1 and surname is %s2"
 * @otherArguments {String | Number}
 * @returns {String}
 */
const parameterizedString = (...args) => {
  const str = args[0];
  const params = args.filter((arg, index) => index !== 0);
  if (!str) return "";
  return str.replace(/%s[0-9]+/g, matchedStr => {
    const variableIndex = matchedStr.replace("%s", "") - 1;
    return params[variableIndex];
  });
}

Exemplos

parameterizedString("my name is %s1 and surname is %s2", "John", "Doe");
// returns "my name is John and surname is Doe"

parameterizedString("this%s1 %s2 %s3", " method", "sooo", "goood");
// returns "this method sooo goood"

Se a posição variável mudar nessa sequência, essa função também será compatível sem alterar os parâmetros da função.

parameterizedString("i have %s2 %s1 and %s4 %s3.", "books", 5, "pencils", "6");
// returns "i have 5 books and 6 pencils."
fatihturgut
fonte
2
var user = "your name";
var s = 'hello ' + user + ', how are you doing';
Termi
fonte
Eu vejo alguns problemas com isso; ele usa concatenação em vez de formatação de string, o que é uma bandeira vermelha para mim ao fazer revisões de código, pois geralmente é mais difícil de ler e manter. Além disso, você não pode armazenar com segurança esse "padrão" em um sistema de recuperação (como um arquivo de configuração ou banco de dados) e injetar o valor do usuário posteriormente.
Rory Browne
1

Aqui está um exemplo de literal de cadeia de várias linhas no Node.js.

> let name = 'Fred'
> tm = `Dear ${name},
... This is to inform you, ${name}, that you are
... IN VIOLATION of Penal Code 64.302-4.
... Surrender yourself IMMEDIATELY!
... THIS MEANS YOU, ${name}!!!
...
... `
'Dear Fred,\nThis is to inform you, Fred, that you are\nIN VIOLATION of Penal Code 64.302-4.\nSurrender yourself IMMEDIATELY!\nTHIS MEANS YOU, Fred!!!\n\n'
console.log(tm)
Dear Fred,
This is to inform you, Fred, that you are
IN VIOLATION of Penal Code 64.302-4.
Surrender yourself IMMEDIATELY!
THIS MEANS YOU, Fred!!!


undefined
>
Amor e paz - Joe Codeswell
fonte
É chamado de um modelo de cadeia , e você pode querer apenas upvote esta resposta existente
Bergi
Este exemplo de "string de modelo" que mostrei IS é uma "string de modelo" que usa um literal de string de várias linhas.
Love and peace - Joe Codeswell