Qual è la logica / storia per il # convenzione di individuare metodi in Ruby?
-
30-09-2019 - |
Domanda
Metodi Per esempio, ho sempre visto indicati come String#split
, ma mai String.split
, che sembra un po 'più logico. O forse anche String::split
, perché si potrebbe prendere in considerazione #split
di essere nello spazio dei nomi di String
. Ho anche visto il metodo da solo, quando la classe è assunto / implicito (#split
).
I capire che questo è il modo in cui i metodi sono identificati in RI. E 'nato prima?
E 'questo per differenziare, ad esempio, i metodi da campi? Ho anche sentito dire che questo aiuta differenzia metodi di istanza da metodi di classe. Ma dove ha fatto questo inizio?
Soluzione
La differenza indica come si accede ai metodi.
I metodi di classe usare il separatore ::
per indicare che il messaggio può essere inviato all'oggetto classe / modulo, mentre metodi di istanza usare il separatore #
per indicare che il messaggio possa essere inviato a un oggetto istanza.
ho intenzione di scegliere la classe Complex
(in Ruby 1.9) per dimostrare la differenza. Hai sia Complex::rect
e Complex#rect
. Questi metodi hanno arity diverse e servono scopi completamente diversi. Complex::rect
prende una vera e un argomento immaginario, restituendo una nuova istanza di Complex
, mentre Complex#rect
restituisce un array di componenti reale e immaginaria dell'istanza.
ruby-1.9.1-p378 > x = Complex.rect(1,5)
=> (1+5i)
ruby-1.9.1-p378 > x.rect
=> [1, 5]
ruby-1.9.1-p378 > x.rect(2, 4) # what would this even do?
ArgumentError: wrong number of arguments(2 for 0)
from (irb):4:in `rect'
from (irb):4
from /Users/mr/.rvm/rubies/ruby-1.9.1-p378/bin/irb:17:in `<main>'
Credo il motivo che non usano .
come separatore per tutto è che sarebbe ambiguo se il metodo appartiene ad una classe o un'istanza. Ora che mi sono abituato a Ruby di fare questo, io in realtà lo vedo come un inconveniente di convenzioni altre lingue, ad essere onesti.
Inoltre, questo è un po 'un argomento completamente indipendenti da campi a causa di tutti i messaggi è possibile inviare sono messaggi, propriamente parlando, anche se aspetto come un campo accessibile al pubblico . La cosa più vicina che devi campi sono attributi o variabili di istanza, naturalmente, che sono sempre preceduti da @
e non sono direttamente accessibile dall'esterno l'istanza a meno che non si sta utilizzando l'ereditarietà o Object#instance_variable_get
/ _set
.
Per quanto riguarda specificamente il motivo per cui ha scelto ::
e #
? ::
senso per me perché convenzionalmente separato namespace, ma #
probabilmente era solo un simbolo che non è stato utilizzato in altri nomenclatura e potrebbe essere inequivocabilmente riconosciuto come un separatore esempio metodo.
Altri suggerimenti
I capire che questo è il modo in cui i metodi sono identificati in RI. E 'nato prima?
Sì, questo è dove è venuto. Quando si utilizza #
, è collegamenti ipertestuali automaticamente i vostri metodi, in modo da riferimenti ad altri metodi di documentazione ha cominciato ad essere preceduto dal segno #
. Vedere qui :
I nomi delle classi, file sorgenti, e le eventuali nomi di metodo che contengono un carattere di sottolineatura o preceduti da un carattere cancelletto vengono automaticamente collegamenti ipertestuali dal testo di commento alla loro descrizione.
Non è possibile in realtà invocare un metodo in questo modo, però. Ma questo non dovrebbe essere sorprendente; dopo tutto, <cref ...>
è un'istruzione non valida in C #, pur essendo un tag documentazione valida.