2017-09-28 2 views
0

Ich habe zwei IFFE:Wie durch Verweis übergeben oder emulieren es

var Helper = (function() { 
    return { 
     number: null, 
     init: function (num) { 
      number = num; 
     } 
    } 
})(); 

var Helper2 = (function() { 
    return { 
     options: { 
      number: [], 
     }, 
     init: function(num){ 
      this.options.number = num; 
     }, 
     getData: function() { 
      return this.options.number; 
     } 
    } 
})(); 


Helper2.init(Helper.number); 
console.log(Helper2.getData()); 
Helper.init(5); 
console.log(Helper2.getData()); 

Was ich will, ist

Helper2.init(Helper.number); 
console.log(Helper2.getData()); // null 
Helper.init(5); 
console.log(Helper2.getData()); // 5 

was ich

ist
Helper2.init(Helper.number); 
console.log(Helper2.getData()); // null 
Helper.init(5); 
console.log(Helper2.getData()); // null 

Welche Techniken getan werden kann, um es als Referenz weitergeben zu lassen, wenn es möglich ist?

JSBIN: https://jsbin.com/gomakubeka/1/edit?js,console

Edit: Vor Tonnen von Menschen beinhaltet verschiedene Arten starten Helper2 depend on Helper zu haben, die tatsächliche Umsetzung von Helper unbekannt ist und konnte 100 von Möglichkeiten, haben sie die Zahl implementieren, so Helper2 die Speicheradresse benötigt.

Edit 2: Ich nehme an, der Weg, den ich hatte gehofft, einige Start auszukommen war zu wissen, dass Arrays/Objekte als Referenz übergeben bekomme, wie kann ich diese primitive Art wickeln in einer Weise, dass ich durch Verweis

verwenden können
+0

Was ist konkret über den Code, den Sie haben? Wenn Sie sagen, dass es Hunderte von Möglichkeiten gibt, wie 'Helfer' die Zahl implementieren kann, bedeutet das, dass das aktuelle Schema ist, dass' Helfer' immer ein Attributrecht auf der Wurzel des Objekts vom 'Zahl' -Typ hat? – zero298

+0

Warum kapseln Sie Helper nicht direkt in Helper2 ein? –

+0

@ zero298 Ja. Es kann in einer Variablen mit dem Namen '.randomNumber' in jemand anderen Implementierung von' Helfer' sein. @ Jean-BaptisteYunès Ich würde eine Schnittstelle benötigen, die einen gemeinsamen Weg hat, um den gewünschten Wert zu erhalten, aber es gibt keine Schnittstelle (und Es gibt keinen strikten Weg, AFIK in js) zu machen. – CuriousDeveloper

Antwort

0

Zunächst einmal warum funktioniert es nicht:

helper ist eine selbst aktivierende Funktion, die ein Objekt zurückgibt. Wenn init aufgerufen wird, wird eine Zahl auf das Objekt Helper gesetzt.

Dann übergeben Sie in Helper2 eine ganze Zahl() an init das Objekt auf null setzen. Sie übergeben den Verweis nicht an Helper.number. Nur der Wert, der darauf festgelegt wurde.

Sie müssen das ganze Objekt an es übergeben und es auslesen.

Ein Beispiel:

var Helper = (function() { 
 
    return { 
 
     number: null, 
 
     init: function (num) { 
 
      this.number = num; //add this 
 
     } 
 
    } 
 
})(); 
 

 
var Helper2 = (function() { 
 
    return { 
 
     options: { 
 
      number: [], 
 
     }, 
 
     init: function(obj){ 
 
      
 
      this.options = obj; //save a reference to the helper obj. 
 
     }, 
 
     getData: function() { 
 
      if (this.options.number) 
 
      { 
 
       return this.options.number; 
 
      } 
 
     } 
 
    } 
 
})(); 
 

 

 
Helper2.init(Helper); //store the helper object 
 
console.log(Helper2.getData()); 
 
Helper.init(5); 
 
console.log(Helper2.getData());

+0

Dies beruht auf einer bestimmten Schnittstelle, der Helper entsprechen muss, damit Helper2 weiß, wie die Variable benannt ist. Zum Beispiel ist es möglich, dass Helper.thisisthenumber ist, wo die Nummer, die ich will, gespeichert ist. Leider sind Interfaces nicht etwas in Javascript, also habe ich keinen Vertrag zwischen den beiden Objekten – CuriousDeveloper

+0

Du hast Recht. Dafür gibt es Lösungen. Wenn etwas generisch sein soll, benötigt es mehr Codezeilen. Untersuchen Sie die Prototyp-Vererbung. – Mouser

1

Passing durch Bezugnahme in JavaScript kann nur auf Objekte passieren. Das einzige, was Sie in JavaScript an Wert übergeben können, sind primitive Datentypen.

Wenn Sie auf Ihrem ersten Objekt die "number: null" so geändert haben, dass sie innerhalb eines Optionsobjekts wie in Ihrem zweiten Objekt verschachtelt ist, können Sie eine Referenz dieses Objekts an das andere Objekt übergeben. Der Trick ist, wenn Sie benötigen, um Verweis auf Objekte und nicht primitive Datentypen zu übergeben. Verschachteln Sie stattdessen die primitiven Datentypen in Objekten und verwenden Sie die Objekte.

Ich änderte Sie ein wenig Code, aber ich denke, das funktioniert für das, was Sie erreichen wollten.

var Helper = function (num) { 
 
    return { 
 
     options: { 
 
      number: num 
 
     }, 
 
     update: function (options) { 
 
      this.options = options; 
 
     } 
 
    } 
 
}; 
 

 
var Helper2 = function (num) { 
 
    return { 
 
     options: { 
 
      number: num, 
 
     }, 
 
     update: function(options){ 
 
      this.options = options; 
 
     }, 
 
     getData: function() { 
 
      return this.options.number; 
 
     } 
 
    } 
 
}; 
 

 
var tempHelp = new Helper(); 
 
var tempHelp2 = new Helper2(); 
 
tempHelp2.update(tempHelp.options); 
 
tempHelp.options.number = 5; 
 
console.log(tempHelp2.getData());

+0

Hallo, willkommen in SO. Große Antwort, nahm die Freiheit, Ihre Antwort in ein Code-Snippet zu setzen, damit die Leute das Ergebnis sehen können. – Mouser

+0

Vielen Dank und danke, dass Sie es in ein Code-Snippet eingefügt haben. –

0

Ich glaube nicht, dass Sie genau das zu bekommen, in der Lage sein werden, was Sie wollen.Doch in einem Ihrer Kommentare sagte Sie:

Leider Schnittstellen sind nicht etwas in JavaScript

Das ist nicht ganz richtig ist. Ja, es gibt keine starke Eingabe und die Benutzer Ihres Codes können Ihre Vorschläge vollständig ignorieren, wenn Sie sagen, dass eine Funktion einen bestimmten Objekttyp benötigt.

Aber Sie können immer noch eine Art von Schnittstelle erstellen, von der Benutzer erweitert werden sollen, um mit Ihrem eigenen Code zu spielen. Sie können Benutzern beispielsweise mitteilen, dass sie extend aus der Klasse Valuable mit einem Mechanismus für den Zugriff auf eine berechnete value-Eigenschaft bereitstellen müssen, bei der es sich um eine Reference Instanz handelt, die ein primitives Element kapseln kann. .

Da dies berechnete Eigenschaften verwendet, hat dies auch den Vorteil, die Notation .value zu nutzen. Die Sache ist, dass die .value eine Reference anstelle des tatsächlichen Wertes sein wird.

// Intermediary class that can be passed around and hold primitives 
 
class Reference { 
 
    constructor(val) { 
 
    this.val = val; 
 
    } 
 
} 
 

 
// Interface that dictates "value" 
 
class Valuable { 
 
    constructor() { 
 
    this._value = new Reference(); 
 
    } 
 
    get value() { 
 
    return this._value; 
 
    } 
 
    set value(v) { 
 
    this._value.val = v; 
 
    } 
 
} 
 

 
// "Concrete" class that implements the Valuable interface 
 
class ValuableHelper extends Valuable { 
 
    constructor() { 
 
    super(); 
 
    } 
 
} 
 

 
// Class that will deal with a ValuableHelper 
 
class Helper { 
 
    constructor(n) { 
 
    this.options = { 
 
     number: n 
 
    } 
 
    } 
 
    getData() { 
 
    return this.options.number; 
 
    } 
 
    setData(n) { 
 
    this.options.number = n; 
 
    } 
 
} 
 

 
// Create our instances 
 
const vh = new ValuableHelper(), 
 
    hh = new Helper(vh.value); 
 

 
// Do our stuff 
 
console.log(hh.getData().val); 
 
vh.value = 5; 
 
console.log(hh.getData().val); 
 
hh.setData(vh.value); 
 
vh.value = 5;

+0

Ich bin auf ES5 beschränkt, aber ich werde schauen, was möglich ist – CuriousDeveloper

Verwandte Themen