2013-06-14 16 views
6

Zastanawiasz się, czy istnieje sposób na użycie makr w Rubim, który dokonuje zastępowania tekstu w taki sposób, w jaki C działałoby?Makra w Ruby?

Na przykład:

define ARGS 1,2 
sum(ARGS) # returns 3 

EDIT: Dokładniej mój problem wygląda bardziej jak:

@button1 = FXButton.new(self, "Button 1",:opts => BUTTONPROPERTIES,:width => width, :height => height) 
@button2 = FXButton.new(self, "Button 2",:opts => BUTTONPROPERTIES,:width => width, :height => height) 
@button3 = FXButton.new(self, "Button 3",:opts => BUTTONPROPERTIES,:width => width, :height => height) 

i idealnie chciałbym kod wyglądać:

@button1 = FXButton.new(self, "Button 1", ALLBUTTONPROPERTIES) 
@button2 = FXButton.new(self, "Button 2", ALLBUTTONPROPERTIES) 
@button3 = FXButton.new(self, "Button 3", ALLBUTTONPROPERTIES) 

Zauważ, jak mam zmienne "width" i "height", które nie zostaną poprawnie przekazane do alizację klasy FXButton, jeśli ustawię ją na pewną uprzednio określoną wartość. Czy istnieje jakiś rodzaj zastępowania kodu, który zajmowałby się tym problemem?

+4

Czy możesz opisać * problem *, który próbujesz rozwiązać w/Ruby? W takim razie możemy lepiej odpowiedzieć na pytanie. – Pete

+0

Rzeczywistym "problemem" jest to, że wielokrotnie wpisuję te same wartości dla 3 argumentów w funkcji i tylko ją zmieniam. Problem polega na tym, że niektóre z tych samych argumentów, które piszę, są zmienne. – thecooltodd

Odpowiedz

9

Nie potrzebujesz makro. Po prostu określ zmienną lub stałą.

A = [1, 2] 
A.inject(:+) # => 3 

Po edycji na swoje pytanie

Można zrobić tak:

ALLBUTTONPROPERTIES = ->{{opts: => BUTTONPROPERTIES, width: width, height: height}} 

oraz w kontekście, w którym stałe i zmienne BUTTONPROPERTIES, width, height są przypisana pewna wartość, zrób to:

@button1 = FXButton.new(self, "Button 1", ALLBUTTONPROPERTIES.call) 
@button2 = FXButton.new(self, "Button 2", ALLBUTTONPROPERTIES.call) 
@button3 = FXButton.new(self, "Button 3", ALLBUTTONPROPERTIES.call) 
+0

Do czego służy połączenie? Nigdzie nie mogę tego znaleźć. Czy to ponowne przypisanie wartości szerokości i wysokości? Co robi operator ->? Dzięki jeszcze raz. – thecooltodd

+0

'-> {...}' nazywa się lambda. Tworzy obiekt 'Proc'. Nie jest oceniany przy jego tworzeniu. 'call' ocenia je w danym kontekście. – sawa

+0

Idealny! Nie miałem pojęcia, jaka była składnia tworzenia lambda. Dzięki. Najlepsza odpowiedź. – thecooltodd

7

W ruby ​​nie ma preprocesu, makra nie mają sensu. Po prostu użyj stałej ciągów lub innego rodzaju stałej, której potrzebujesz.

7

Prawdopodobnie istnieje inny sposób obejścia tego, co próbujesz zrobić. Makra preprocesorów nie mają sensu, ponieważ Ruby nie jest językiem skompilowanym, jest językiem interpretowanym.

Szczególnie dla przykładu istnieje bardzo czysty sposób, aby to zrobić:

args = [1, 2] 
sum(*args) # equivalent to sum(1, 2) 
+2

Jak dotąd jest to najlepsza odpowiedź, jaką otrzymałem.Prawie dokładnie to, czego szukam. – thecooltodd

+2

+1 za udzielenie prostej i pomocnej odpowiedzi. –

+0

@downvoter, proszę o wyjaśnienie? – Shoe

3

Ruby sposobem rozwiązania problemu będzie prawdopodobnie nieco różni się od podejścia:

@buttons = ["Button 1", "Button 2", "Button 3"].map do |name| 
    FXButton.new(self, name, 
       :opts => BUTTONPROPERTIES, 
       :width => width, 
       :height => height) 
end 

W tym przykładzie nie masz zmiennych @button1, @button2, @button3. Zamiast tego @buttons jest tablicą zawierającą wszystkie trzy.

+0

Zdaję sobie sprawę, że nie wyjaśniłem w pełni mojego problemu. Nawet jeśli zrobię to dla przycisków 1-3, być może będę musiał wykonać kolejne 3 przyciski w zupełnie innej klasie (nie tylko instancję), więc będę musiał przepisać cały ten kod jeszcze. – thecooltodd