La rubena metaklaso
La metaklaso estas interesa temo en Rubeno. Ĉiu objekto havas metaklason kaj ĝi situas inter objekto kaj sia klaso, sed ĝi ŝajnas kaŝiĝi. La metaklaso ne estas rekte atingebla per la sintakso, oni sole nerekte povas efiki ĝin. Kio ĝi estas kaj kiel ĝi utilas?
Kunteksto
En la Rubena programlingvo, ĉio estas objekto. Ŝajnas memevidenta, eĉ se tio ne veras en Ĝavo aŭ Pitono, kie la bazaj datumtipoj ne estas objektoj. Interese, en Rubeno ĉiu objekto ankaŭ havas klason, kiu ne nepre sekvas el ĉio estas objekto. Kiam oni kreas klason, tiu klaso estas objekto de la klaso Klaso
aŭ Class
.
Ĉu ekzistas la Metaklaso?
Se la metaklaso kaŝiĝas inter la objekto kaj la klaso, ĉu ĝi nur estas malekstera rubena afero. Fakte ne, estas kelkaj metodoj atingi ĝin. Jen ekzemplo:
class Homo
def initialize(familia_nomo)
@familia_nomo = familia_nomo
end
def familia_nomo
@familia_nomo
end
end
ludwik = Homo.new("Zamenhof")
marjorie = Homo.new("Boulton")
De tie, ni povas voki familia_nomo
kaj ĝi liveras al ni kion ne anticipas.
ludwik.familia_nomo #=> "Zamenhof"
marjorie.familia_nomo #=> "Boulton"
Sed, familia_nomo
apartenas al la klaso Homo. Por malfermi la metaklason, ni bezonas uzi specifin sintakson class << objekto
.
class << ludwik
def persona_nomo
"Ludwik"
end
end
Poste, ludwik havos funkcion persona_nomo
ludwik.persona_nomo #=> "Ludwik"
sed ne marjorie
marjorie.persona_nomo
> NoMethodError: undefined method `persona_nomo' for #<Homo:0x007fbbfc229e98 @familia_nomo="Boulton">
> from (irb):31
> from /usr/bin/irb:11:in `<main>'
Kial? Ni difinis persona_nomo
je la metaklaso de ludwik kaj la metaklaso apartenas al ludwik kaj ne apartenas al marjorie.
Ĉu valoras?
Meti funkciojn je la metaklaso de objekto rompas reuzadon de funkciojn je klasoj, kiu estas forto de objektemaj/klasaj sistemoj, ĉu ne? Je datumobjektoj, jes, almenaŭ mi uzas ilin malofte. Sed, ĉu vi memoras dum la kunteksta sekcio ke eĉ klasoj estas objektoj de la klaso Class
? Klasa nivelo funkcioj fakte apartenas al la metaklaso de la objekto de la Class
, oj. Eble ekzemplo helpos:
Por aldoni funkcion al klason, ni povas difini ĝin sekve:
class Homo
def self.planedo
"La Tero"
end
end
Tio egalas al:
class << Homo
def planedo
"La Tero"
end
end
Do ĉiu klasa nivela funkcio estas funkcio je metaklaso. La samaĵoj estas
ludwik estas objekto de la klaso Homo,
Homo estas objekto de la klaso Class
Kaj
persona_nomo estas funkcio je la metaklaso de ludwik
planedo estas funkcio je la metaklaso de Homo
La metaklaso uziĝas multe en ĉiutaga programado, eĉ se la programistoj ne notas tion. Estas multe pli diri pri la metaklaso, sed mi pensas ke tio sufiĉas por nun.