Sürekli atamanın dahili olarak nasıl çalıştığına bir göz atalım. Takip eden kod, ruby-1.9.3-p0'un bir kaynak tarball'undan çıkarılır. Öncelikle (sabitlerini atamak için kullanılır) VM talimatı setconstant
tanımına bakalım:
# /insns.def, line 239
DEFINE_INSN
setconstant
(ID id)
(VALUE val, VALUE cbase)
()
{
vm_check_if_namespace(cbase);
rb_const_set(cbase, id, val);
INC_VM_STATE_VERSION();
}
burada vm_check_if_namespace
veya INC_VM_STATE_VERSION
bir kanca yerleştirmek için hiçbir fırsatı. Bu yüzden rb_const_set
bakmak (variable.c: 1886), her bir sabit atanır denir işlevi: Hatta sabit atandı ilk kez çağrılmadı tüm kodu kaldırıldı
# /variable.c, line 1886
void
rb_const_set(VALUE klass, ID id, VALUE val)
{
rb_const_entry_t *ce;
VALUE visibility = CONST_PUBLIC;
# ...
check_before_mod_set(klass, id, val, "constant");
if (!RCLASS_CONST_TBL(klass)) {
RCLASS_CONST_TBL(klass) = st_init_numtable();
}
else {
# [snip], won't be called on first assignment
}
rb_vm_change_state();
ce = ALLOC(rb_const_entry_t);
ce->flag = (rb_const_flag_t)visibility;
ce->value = val;
st_insert(RCLASS_CONST_TBL(klass), (st_data_t)id, (st_data_t)ce);
}
bir modülün içinde. Daha sonra buna göre çağrılan tüm fonksiyonlara baktım ve Ruby kodundan bir kanca yerleştirebileceğimiz tek bir nokta bulamadım. Bu, bir şeyi kaçırmadığı sürece, bir sabit atamayı (en azından MRI'da) no no'lu yoldan çıkarmanın zor gerçek olduğu anlamına gelir.
Güncelleme
netleştirmek için: Anonim sınıf (Andrew yanıtında doğru belirtildiği gibi) atanır atanmaz sihirli kısa sürede yeni bir isim alamadım yapar. Aksine, sınıfın nesne kimliği ile birlikte sabit isim, Ruby'nin dahili sabit arama tablosunda saklanır. Bundan sonra, sınıfın adı istenirse, artık uygun bir adla (ve sadece Class:0xXXXXXXXX...
) çözülebilir.
Bu ödeve yanıt vermek için yapabileceğiniz en iyi şey, nil
olmayan (bu büyük bir kaynak israfı olan IMHO olana kadar) arka plan çalışanı iş parçacığının döngüsünde sınıfın name
numarasını denetlemektir.
Çok ilginç bir soru. –
AFAIK, değişken atamalar için sabit veya başka bir şekilde hala kanca yok ([aynı soru için uzun süre önce buraya bakın] (http://www.ruby-forum.com/topic/65720)). Globals, evet. –