5

Sto cercando di ottenere un oggetto JavaScript per utilizzare le "questo" assegnazioni del costruttore di un altro oggetto, nonché di assumere il prototipo di tutti gli oggetti funzioni. Ecco un esempio di quello che sto cercando di realizzare:La funzione Javascript che utilizza "this =" restituisce "Lato sinistro non valido nell'assegnazione"

/* The base - contains assignments to 'this', and prototype functions 
    */ 
function ObjX(a,b) { 
    this.$a = a; 
    this.$b = b; 
} 

ObjX.prototype.getB() { 
    return this.$b; 
} 

function ObjY(a,b,c) { 
    // here's what I'm thinking should work: 
    this = ObjX(a, b * 12); 
    /* and by 'work' I mean ObjY should have the following properties: 
    * ObjY.$a == a, ObjY.$b == b * 12, 
    * and ObjY.getB == ObjX.prototype.getB 
    * ... unfortunately I get the error: 
    *  Uncaught ReferenceError: Invalid left-hand side in assignment 
    */ 

    this.$c = c; // just to further distinguish ObjY from ObjX. 
} 

Sarei grato per i tuoi pensieri su come avere ObjY sussumere le assegnazioni di ObjX a 'questo' (cioè non deve ripetere tutte le this.$* = * assegnazioni in ObjY's constructor) e ObjY assume ObjX.prototype.

Il mio primo pensiero è quello di provare la seguente:

function ObjY(a,b,c) { 
    this.prototype = new ObjX(a,b*12); 
} 

Idealmente mi piacerebbe imparare a fare questo in modo prototipale (cioè non devono utilizzare uno qualsiasi di questi sostituti 'classici' come OOP Base2).

Può essere interessante notare che ObjY sarà anonima (per esempio factory['ObjX'] = function(a,b,c) { this = ObjX(a,b*12); ... }) - se ho la terminologia giusta.

Grazie.

+1

correlati: [? Perché non è possibile assegnare un nuovo valore a “questo” in un prototipo di funzione] (http: // stackoverflow.com/q/9713323/1048572) – Bergi

risposta

15

Non si può davvero farlo, perché il valore this per definizione è immutabile, non è possibile modificare in questo modo a cosa fa riferimento.

Una soluzione sarebbe quella di utilizzare i call o apply metodi per eseguire la funzione ObjX costruzione nella this oggetto di ObjY:

function ObjY(a,b,c) { 
    ObjX.call(this, a, b * 12); 
    this.$c = c; 
} 

Nell'esempio precedente, viene eseguita la funzione ObjX cambia di valore this, quindi tutte le estensioni di proprietà apportate a quell'oggetto in questa funzione si rifletteranno nel nuovo oggetto che il valore this fa riferimento al costruttore ObjY.

Non appena termina il metodo call, l'oggetto this verrà aumentato e sarà possibile creare più estensioni di proprietà, ad esempio aggiungendo il valore $c.

Edit: Circa i prototipi, il campione non funzionerà, perché la proprietà prototype non ha alcun significato speciale per oggetto in posizioni sarà proprio come qualsiasi altra proprietà, dovrebbe essere utilizzato su funzioni di costruzione.

Penso che potresti confondere la proprietà prototype dei costruttori con la proprietà interna [[Prototype]] di cui dispongono tutti gli oggetti.

La proprietà [[Prototype]] può essere impostata solo dal new operatore (attraverso il funzionamento interno [[Construct]]), questa struttura non può essere modificata, (anche se alcune implementazioni, come quello Mozilla, è possibile accedere attraverso obj.__proto__;, e ECMAScript 5, è stato introdotto il metodo Object.getPrototypeOf, ma non ti consiglierei di fare confusione direttamente con esso).

realtà, quando viene eseguita la funzione di costruzione, la [[Prototype]] struttura interna dell'oggetto che il valore this riferisce, è già stato impostato alla proprietà di suo costruttore prototype.

Così, come commenti @Anurag, è possibile impostare il ObjY.prototype a un ObjX oggetto appena creato:

function ObjY(a,b,c) { 
    ObjX.call(this, a, b * 12); 
    this.$c = c; 
} 

ObjY.prototype = new ObjX(); 
ObjY.prototype.constructor = ObjY; 

che renderanno il vostro ObjY ereditano anche le proprietà aggiunto alla ObjX.prototype, e come potete vedere, Ho modificato lo ObjY.prototype.constructor, poiché l'assegnazione nella riga sopra renderà questa proprietà erroneamente indirizzata a ObjX.

articoli consigliati:

+1

Grazie CMS. Ottimo collegamento, anche. L'altra domanda è come assegnare i prototipi - può essere fatto all'interno del costruttore? –

+0

@ Brian, prego, sì, ho avuto un refuso! – CMS

+0

@Brian, imposta un oggetto di ObjX come prototipo di ObjY, per ottenere anche i suoi metodi. 'ObjY.prototype = new ObjX;'. Metodi e proprietà se non trovati nell'oggetto corrente, vengono cercati nella catena del prototipo. – Anurag