2009-03-08 10 views
18

Uświadomiłem sobie można mieć właściwość w perspektywie obiektu automatycznie tak:Javascript - inicjator obiektu?

var obj = { 

    init:(function(){ alert('loaded');})(); 

} 

Próbuję użyć tej metody jako inicjator dla obiektu. Problem, który napotykam, przekazuje odwołanie do 'obj' do właściwości init. Podejrzewam, że generuje błędy, ponieważ obiekt nie został jeszcze całkowicie zbudowany w przeglądarce. Próbuję wykonać następujące czynności, ale bezskutecznie. Jeśli istnieje sposób, aby to zrobić, chciałbym wiedzieć, jak.

var obj = { 
    prop:function(){ alert('This just ran.'); }, 
    init:(function(){ obj.prop(); })(); 
} 

Odpowiedz

21

Jeśli chcesz utworzyć wiele instancji podobne obiekty, powinieneś używać zwykłych starych funkcji konstruktora (pamiętaj, aby umieścić właściwości wspólne w prototypie!).

Jeśli chcesz utworzyć pojedynczy obiekt, rozważ użycie anonimowego konstruktora. Twój przykład byłoby przeczytać:

var obj = new (function() { 
    this.prop = function() { 
     alert('This just ran.'); 
    } 

    // init code goes here: 
    this.prop(); 
}); 

Ma to dodatkową zaletę nad literałów obiektowych: funkcja konstruktora może być stosowany jako zamknięcie ponad zmiennych „prywatny”.

Nie nadużywaj literałów obiektowych: mogą sprawić, że proste rzeczy będą proste, ale skomplikowane rzeczy staną się zbyt skomplikowane.

+0

Interesujące. Czy wiesz, gdzie mogę znaleźć dokumentację dotyczącą anonimowych konstruktorów? –

+1

@JW, Wierzę, że anonimowy konstruktor jest po prostu anonimową funkcją używaną jako konstruktor (to znaczy wywoływana za pomocą słowa kluczowego 'new'). Zobacz także http://stackoverflow.com/questions/20057431/javascript-anonymous-constructor-function-function i http://enfinery.com/30/javascript-the-case-of-an-anonymous-constructor – iX3

-1

Czy to działa, jeśli przekazujesz "to" do funkcji init?

coś takiego: (niesprawdzone)

var obj = { 
    prop:function(){ alert('This just ran.'); }, 
    init:(function(o){ o.prop(); })(this); 
} 
+2

Nah. Przekazywanie (this) jest odwołaniem do window.object – Geuis

+1

Nie ma bezpośredniego związku, ale możesz szybko prototypować i testować rzeczy używając http://jsfiddle.net/ – Audrius

0

Myślę, że chcesz spróbować czegoś takiego:

var obj = { 
    prop: function() { alert('This just ran.'); }, 
    init: function() { obj.prop(); } 
} 

Object literały reqire oddzielonych przecinkami członkami bez średnikami.

+0

, które nie będą uruchamiać funkcji init podczas tworzenia –

+0

Masz rację - nie ma nie można tego zrobić za pomocą literałów obiektowych. –

5

Nie jest to możliwe: obiekt nie istnieje, dopóki cały blok nie zostanie zinterpretowany.

3

Dlaczego nie można użyć modelu contructor (faktycznie, nie mam pojęcia o jego prawidłowym nazwa):

function Obj() { 
    // Initialising code goes here: 
    alert('Loaded!'); 

    // ... 

    // Private properties/methods: 
    var message = 'hello', 
     sayHello = function() { 
      alert(message); 
     }; 

    // Public properties/methods: 
    this.prop = function() { 
     sayHello(); 
    }; 

    // Encapsulation: 
    this.setMessage = function(newMessage) { 
     message = newMessage; 
    }; 
} 

Zastosowanie:

var instance = new Obj(); 
instance.setMessage('Boo'); 
instance.prop(); 
+0

Powodem nie zainicjowania w konstruktorze jest to, że musisz wywołać konstruktora za każdym razem, gdy potrzebujesz prototypu (np. Do utworzenia podklasy) - funkcja XObj() {...}; XObj.prototype = new Obj() ;. Naprawdę nie chcesz zainicjować rzeczywistej instancji w tym przypadku. – bobince

2

Tak, obiekt wydaje się istnieć lokalnie dopiero później. To zadziałało dla mnie z setTimeout. Testowane ok na IE8, FF5, Chrome 12, Opera v11.5. Nie jestem pewien co do 50 milisekund, ale wyobrażam sobie, że to wystarczy.

var obj = { 
    prop: function() { alert('This just ran.') }, 
    init: (function(){ setTimeout(function(){obj.prop()},50) })() 
} 
+0

Wygrał Działa, jeśli następna linia za instrukcją 'var' musi używać' obj.prop'. – nnnnnn

1

Init w jQuery podobny styl

(function() { 

var $ = function(){ 
    return new $.fn.init(); 
}; 

$.fn = $.prototype = { 
    init: function(){ 
    this.prop(); 
    }, 
    i: 0, 
    prop: function(){ 
    alert('This just ran. Count: ' + (++this.i)); 
    return this; 
    } 
}; 

$.fn.init.prototype = $.fn; 

$().prop().prop(); 

})(); 

jsbin.com

4

Prosta alternatywa:

var obj = { 

    init: function(){ 
    alert('loaded'); 
    } 

}.init(); 
+2

Zwracając uwagę, że to ustawia 'obj' na dowolną wartość' init() 'zwraca - która w tym przykładzie jest' niezdefiniowana'. – nnnnnn

1

to jest aktualizacja do przykładu przedstawionego przez user1575313.

Oryginalny kod działa, ale ogranicza korzystanie z obiektu po zakończeniu konfiguracji.Zwracając odwołanie do obiektu w metodzie init, pozwala on na użycie obiektu poza obiektem.

link do jsFiddle. jsFiddle

var obj = { 

init: function() 
{ 
    alert('loaded'); 

    this.consoleLog(); 

    /* we want to return this to keep object 
    usable after auto init */ 
    return this; 
}, 

consoleLog: function() 
{ 
    console.log(1); 
} 

}.init(); 

/* the obj should now be usable outside the auto init */ 
obj.consoleLog();