2012-12-19 9 views
25

Istnieje kilka klas Ruby, które nie zezwalają na definiowanie metod singletowych na swoich instancjach. Na przykład, Symbol:Dlaczego pojedynczych metod nie można zdefiniować w Symbole lub Fixnums?

var = :asymbol 

def var.hello 
    "hello" 
end 

# TypeError: can't define singleton method "hello" for Symbol 

Pomyślałem, że może to być ograniczenie wszystkich natychmiastowych wartości, ale wydaje się, aby pracować dla nil, true i false (ale nie przypadki Fixnum lub Bignum):

var = true 

def var.hello 
    "hello" 
end 

var.hello #=> "hello" 

Nie rozumiem, dlaczego Ruby pozwala na definiowanie pojedynczych metod dla określonych klas obiektów, ale nie dla innych.

+0

Wydaje się, że nie jest to po prostu 'Fixnum's, ale dowolny' Numeric'. –

+0

Moją reakcją jest to, że ma coś do zrobienia w/types, które miałyby tę samą wartość niezależnie od kontekstu. Symbol ': fred' będzie zawsze tym samym obiektem symbolu, co" 5 ". Niestety tak samo jest w przypadku "true", więc jest to coś głębszego; Zastanawiam się najpierw, czy jest tak samo w różnych wersjach, a potem zastanawiam się, w jaki sposób wprowadzono stałość każdego typu. –

+0

Dokument dla [Object # singleton_class] (http://ruby-doc.org/core-2.3.0/Object.html#method-i-singleton_class) stwierdza: "Jeśli [odbiorca]" obj "ma wartość" nil " , 'true' lub' false' zwraca odpowiednio 'NilClass',' TrueClass' lub 'FalseClass' .Jeśli' obj' jest 'Fixnum' lub' Symbol', powoduje to 'TypeError'." Jak zauważa @Andrew, żadna wartość liczbowa nie może mieć klasy singleton. 'nil',' true' i 'false' mają klasy singleton (np.' class << false; put self, end # => FalseClass'), ale ponieważ te klasy mają tylko jedną instancję, nie ma sensu rozróżniać między klasa i klasa singleton. –

Odpowiedz

20

Ma to związek z pojęciem zwanym "wartościami bezpośrednimi" opisanym przez Matza jako here.

W rzeczywistości żadne bezpośrednie wartości nie powinny zezwalać na metodę singleton. Jednak w przypadku true, false i nil, istnieją w rzeczywistości klasy singleton, które wycofują te wartości (lub wartość jest faktycznie klasą singleton - nie jestem tego pewien). Można zatem dodać pojedyncze wystąpienia do klasy wsparcia, która manifestuje się tak, jakby była samą wartością. Instancje numeryczne i symboliczne nie są pojedynczymi (oczywiście) i nie mają gdzie trzymać metod singleton.

+0

Hmm, czy wartości "prawda", "fałsz" i "zero" nie są już wartościami bezpośrednimi? Czy masz na to referencję? –

+1

Wygląda na to, że [są to nadal wartości bezpośrednie] (http://www.ruby-doc.org/core-1.9.3/ObjectSpace.html#each_object-method). Faktyczna różnica jest opisana powyżej, patrz aktualizacja. – PinnyM

Powiązane problemy