Ruby: łączenie zmiennych w łańcuch


95

Szukam lepszego sposobu na scalanie zmiennych w łańcuch w Rubim.

Na przykład, jeśli ciąg jest podobny do:

„Theanimal actionsecond_animal "

I mam dla zmiennych animal, actioni second_animalto, co jest preferowanym sposobem na wprowadzenie tych zmiennych w na ciąg?

Odpowiedzi:


240

Idiomatycznym sposobem jest napisanie czegoś takiego:

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

Zwróć uwagę na podwójne cudzysłowy (") otaczające ciąg: to jest wyzwalacz dla Rubiego, aby użył wbudowanego zastępowania znaków zastępczych. Nie możesz ich zastąpić pojedynczymi cudzysłowami (') lub ciąg zostanie zachowany bez zmian.


2
Przepraszam, może za bardzo uprościłem problem. Ciąg zostanie pobrany z bazy danych, a zmienna zależy od wielu czynników. Zwykle użyłbym zamiany na 1 lub dwie zmienne, ale może to być więcej. jakieś pomysły?
FearMediocrity

Konstrukcja # {} jest prawdopodobnie najszybsza (chociaż nadal wydaje mi się to sprzeczne z intuicją). Oprócz sugestii gixa, możesz również łączyć łańcuchy z + lub <<, ale mogą zostać utworzone pewne ciągi pośrednie, co jest kosztowne.
Mike Woodhouse

Najlepszy sposób na interpolację zmiennych
Dragutescu Alexandru

115

Możesz użyć formatowania podobnego do sprintf, aby wstrzyknąć wartości do ciągu. W tym celu ciąg musi zawierać symbole zastępcze. Umieść swoje argumenty w tablicy i użyj jednego z następujących sposobów: (Aby uzyskać więcej informacji, zajrzyj do dokumentacji 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

Możesz nawet jawnie określić numer argumentu i przetasować go wokół:

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

Lub określ argument za pomocą kluczy z krzyżykiem:

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

Zauważ, że musisz podać wartość dla wszystkich argumentów dla %operatora. Na przykład nie możesz uniknąć definiowania animal.


18

Użyłbym #{}konstruktora, zgodnie z innymi odpowiedziami. Chcę również zwrócić uwagę, że jest tu prawdziwa subtelność, na którą należy uważać:

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

Natomiast łańcuchy mogą być tworzone z apostrofami (o czym świadczy first_namei last_namezmiennych, konstruktor może być stosowany wyłącznie w ciągach o cudzysłowach.#{}


13
["The", animal, action, "the", second_animal].join(" ")

to inny sposób na zrobienie tego.


10

Nazywa się to interpolacją ciągów i robisz to w następujący sposób:

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

Ważne: zadziała tylko wtedy, gdy ciąg znaków znajduje się w cudzysłowie („”).

Przykład kodu, który nie będzie działał zgodnie z oczekiwaniami:

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

Dziękujemy za użycie właściwego terminu, aby nowi programiści mogli się nauczyć: interpolacja.
Mike Bethany

3

Standardowy system szablonów ERB może działać w Twoim scenariuszu.

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

Możesz go używać ze zmiennymi lokalnymi, na przykład:

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

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

wyjście byłoby: „The Pies liże Ptak

Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.