2009-05-19 20 views

Odpowiedz

6

Można użyć eval() na to pod warunkiem, że już ogłosił swoją zmienną pierwszy:

>> foo = [] 
>> eval("foo")[1] = "bar" 
>> foo[1] 
=> "bar" 

Oto docs.

5

Nie chcę być negatywny, ale ostrożnie kroczę. Ruby oferuje wiele funkcji do bardzo dynamicznego programowania, takich jak define_method, przechowywanie bloków jako obiektów Proc, które będą nazywane później, itp. Zasadniczo są to czystsze kody i znacznie bezpieczniejsze. 99% czasu przy użyciu eval() jest błędem.

I absolutnie nigdy nie używaj eval() w ciągu zawierającym dane wprowadzone przez użytkownika.

53

Jeśli można wybaczyć znak @ przed nazwą zmiennej, co następuje zadziała:

variable_name = ... # determine user-given variable name 
instance_variable_set("@#{variable_name}", :something) 

To utworzy zmienną o nazwie @whatever, a jego wartość ustawiona :something. :something, oczywiście, może być cokolwiek chcesz. Wygląda na to, że działa w zasięgu globalnym, deklarując spontaniczną instancję Object, która wiąże wszystko (nie mogę znaleźć odniesienia do tego).

Metoda instance_variable_get umożliwia pobranie wartości według nazwy w ten sam sposób.

instance_variable_get("@#{variable_name}") 
+0

Dlaczego '@ # {nazwa_zmiennej} =: coś nie działa? –

+0

Otrzymuję 'nie jest dozwolone jako nazwa zmiennej instancji' dla 'instance_variable_set'. Railsy 3.0.7. –

+0

To jest genialne! –

0

Jak mówi Jason Watkins, wiele osób może szybko użyć eval(), co byłoby poważnym błędem. W większości przypadków możesz użyć techniki opisanej przez Tacka, jeśli zadbałeś o użycie zmiennej instancji klasy zamiast lokalnej.

Zmienne lokalne zazwyczaj nie są dostępne. Wszystko z prefiksem @ lub @@ jest łatwo odzyskiwane.

10

Zamiast tego zrobić bezpośrednio, dlaczego nie rozważyć użycia skrótu zamiast tego. Łańcuch będzie kluczem, a wartość, którą chcesz zapisać, będzie wartością. Coś takiego:

string_values = { } 
some_string = params[:some_string]  # parameter was, say "Hello" 
string_values[some_string] = 42 
string_values       # { 'Hello' => 42 } 
some_number = string_values[some_string] 
some_number        # 42 

Ma to kilka zalet. Po pierwsze, oznacza to, że nie robisz nic magicznego, co może być trudne do zrozumienia później. Po drugie, używasz bardzo typowego języka Rubiego, który jest używany do podobnych funkcji w Railsach.

+0

dokładnie myślę :) –

+0

Huh? Co jeśli chcesz po prostu zapisać "Hello" jako zmienną, która będzie później używana. Gdzie są 42? Wydaje się to zbyt skomplikowane ...chociaż wprawdzie jestem nowicjuszem Rubinowym. – Southerneer

+0

To nie jest pytanie zadawane przez pytającego. Odbierają one ciąg znaków z * runtime * i chcą skojarzyć ten ciąg z wartością. Oczywiście, możesz zhackować system, aby utworzyć zmienną o tej nazwie napisu (z powiązanym z nią zastrzeżeniem błędu sprawdzającym ciąg znaków, aby upewnić się, że jest to poprawny identyfikator), ale sugeruję, że używasz prostego, szeroko rozumianego i bezpiecznego Rubiego. Hash', aby powiązać ciąg i wartość razem. –

2

Teraz po prostu za pomocą metody instance_variable_set można utworzyć zmienną instancji w środowisku wykonawczym.

instance_variable_set('@' + 'users', User.all) 
Powiązane problemy