Ruby: объединение переменных в строку

95

Я ищу лучший способ объединить переменные в строку в Ruby.

Например, если строка выглядит примерно так:

« »animal actionsecond_animal

И у меня есть переменные animal, actionи second_animal, что является предпочтительным способом поместить эти переменные в к строке?

Страх
источник

Ответы:

240

Идиоматический способ - написать что-то вроде этого:

"The #{animal} #{action} the #{second_animal}"

Обратите внимание на двойные кавычки ("), окружающие строку: это триггер для Ruby, чтобы использовать встроенную подстановку заполнителя. Вы не можете заменить их одинарными кавычками ('), иначе строка будет сохранена как есть.

Майк Вудхаус
источник
2
Извините, может я слишком упростил задачу. Строка будет извлечена из базы данных, а переменная зависит от ряда факторов. Обычно я бы использовал замену для одной или двух переменных, но это может быть больше. Есть предположения?
FearMediocrity
Конструкция # {}, вероятно, самая быстрая (хотя мне это все еще кажется нелогичным). Помимо предложения gix, вы также можете собирать строки с помощью + или <<, но могут быть созданы промежуточные строки, что дорого.
Майк Вудхаус,
Лучший способ интерполировать переменные
Александру Драгутеску,
115

Вы можете использовать форматирование, подобное sprintf, для вставки значений в строку. Для этого строка должна включать заполнители. Поместите свои аргументы в массив и используйте один из следующих способов: (Для получения дополнительной информации см. Документацию по Kernel :: sprintf .)

fmt = 'The %s %s the %s'
res = fmt % [animal, action, other_animal]  # using %-operator
res = sprintf(fmt, animal, action, other_animal)  # call Kernel.sprintf

Вы даже можете явно указать номер аргумента и перемешать их:

'The %3$s %2$s the %1$s' % ['cat', 'eats', 'mouse']

Или укажите аргумент с помощью хеш-ключей:

'The %{animal} %{action} the %{second_animal}' %
  { :animal => 'cat', :action=> 'eats', :second_animal => 'mouse'}

Обратите внимание, что вы должны указать значение для всех аргументов %оператора. Например, вы не можете избежать определения animal.

gix
источник
18

Я бы использовал #{}конструктор, как указано в других ответах. Я также хочу отметить, что здесь есть настоящая тонкость, на которую следует обратить внимание:

2.0.0p247 :001 > first_name = 'jim'
 => "jim" 
2.0.0p247 :002 > second_name = 'bob'
 => "bob" 
2.0.0p247 :003 > full_name = '#{first_name} #{second_name}'
 => "\#{first_name} \#{second_name}" # not what we expected, expected "jim bob"
2.0.0p247 :004 > full_name = "#{first_name} #{second_name}"
 => "jim bob" #correct, what we expected

Хотя строки могут быть созданы с одинарными кавычками ( о чем свидетельствует first_nameи last_nameпеременные, конструктор может быть использован только в строках с двойными кавычками.#{}

Старкерс
источник
13
["The", animal, action, "the", second_animal].join(" ")

это еще один способ сделать это.

Эндрю Гримм
источник
10

Это называется строковой интерполяцией, и вы делаете это так:

"The #{animal} #{action} the #{second_animal}"

Важно: это будет работать, только если строка заключена в двойные кавычки ("").

Пример кода, который не будет работать должным образом:

'The #{animal} #{action} the #{second_animal}'
sqrcompass
источник
Спасибо за использование правильного термина, чтобы новые программисты могли узнать: интерполяция.
Майк Бетани
3

Стандартная система шаблонов ERB может работать для вашего сценария.

def merge_into_string(animal, second_animal, action)
  template = 'The <%=animal%> <%=action%> the <%=second_animal%>'
  ERB.new(template).result(binding)
end

merge_into_string('tiger', 'deer', 'eats')
=> "The tiger eats the deer"

merge_into_string('bird', 'worm', 'finds')
=> "The bird finds the worm"
Клинт Пахл
источник
0

Вы можете использовать его со своими локальными переменными, например:

@animal = "Dog"
@action = "licks"
@second_animal = "Bird"

"The #{@animal} #{@action} the #{@second_animal}"

выход будет: «The Dog лижет Птица »

Николас Ла Порта
источник