2016-11-20 2 views
3

In der Perspektive der Rückrufe, bin ich mit einer seltsamen Situation konfrontiert, als ich wusste, dass myDelegate.Target den Verweis auf die Klasse enthält, deren Methode es enthält. (Ich suchte es auf SO, aber ich entschuldige, wenn ich einig Thread bereits verpaßt diese zu beantworten)So sichern Sie Delegaten Instanzreferenz

Zum Beispiel

public delegate void TravePlanDelegate(); 

public class Traveller 
{ 
    //Papa is planing a tour, along with Mama 
    public void Planner() 
    { 
     //Asking me (delegate) to hold a letter about PlanA's detail 
     TravelPlanDelegate myPlan = PlanA; 
     //Sending me to TravelAgency office with letter 
     new TravelAgency().ExecuteTravelPlan(myPlan); 
    } 
    public void PlanA() 
    { 
     //Papa's open plan with Mama 
     Console.WriteLine("First Berline, then New Yark and finally Lahore"); 
    } 
    public void PlanB() 
    { 
     //Papa's secret plan 
     Console.WriteLine("First Dubai, and then Lahore"); 
    } 
} 

public class TravelAgency 
{ 
    public void ExecuteTravelPlan(TravePlanDelegate tp) 
    { 
     Traveller traveller = (Traveller)tp.Target; 
     //Here it should execute plan 
     //tp.Target - A reference to Traveler class, which can lead travel 
     //agency to Papa's secret plan (And exposes it to Mama) 
    } 
} 

In diesem Beispiel Informationen von travel Delegaten geheimen Plan über Papa bekommen. Habe ich das Delegiertenkonzept richtig verstanden oder etwas übersehen?

+0

Gibt es möglicherweise feindlichen .NET-Code in Ihrem Prozess? Oder möchten Sie verhindern, dass API-Interna verloren gehen? – usr

+0

Ich möchte Bibliotheken wie TravelAgency verwenden, aber ich bezweifle, dass sie in Details meiner eigenen Bibliothek gehen können. – Lali

Antwort

2

Ihre Annahme ist richtig. Unglücklicherweise, wie auch immer Sie versuchen, Ihr Objekt zu "kapseln" - es muss immer irgendwo ein Verweis darauf sein, sonst wäre es unmöglich, seine Instanzmethode aufzurufen.

als eine Art Gegenmaßnahme können Sie den Methodenaufruf Proxy auf einen Lambda-Ausdruck:

TravelPlanDelegate myPlan = (args) =>PlanA(args); 

Dies macht es weniger wahrscheinlich, dass jeder Schelm Code auf einige schlecht beabsichtigten Operationen auszuführen versucht, Ihre Code, da Sie wissen, wie Ihr Code im Voraus aussieht, wird es nicht helfen, etwas zu erreichen.

Beachten Sie, dass dies keine Sache gewährleistet, da der erzeugte Delegat noch über eine Target-Eigenschaft für ein Objekt verfügt, das einen Verweis auf Ihren enthält.

Cracker, die schlau genug sind, können immer noch Reflektionen auf die generierte Klasse anwenden und einen Verweis auf Ihr Objekt erhalten.

Fazit:

Nur Code verbrauchen Sie vertrauen - es ist nicht viel von einem Problem in der heutigen Open-Source-getriebene Welt ist.

+0

Lembda-Ausdruck ist eine Möglichkeit, auf eine zu delegierende Funktion zu verweisen. Es hilft nicht, die Privatsphäre zu wahren. Kann es eine bessere Technik geben, wenn ich ein Bibliotheksbauer bin oder am anderen Ende diese Bibliothek benutze? – Lali

+1

Lambda-Ausdruck ist keine Möglichkeit, einen Delegaten auf eine Funktion zu verweisen - er erstellt ein anonymes Objekt mit einer anonymen Methode. Diese Klasse hat einen zufälligen Namen und die Methode, die aufgerufen wird, hat einen zufälligen Namen. Beachten Sie, dass es aufgrund der Argumentation, die ich im ersten Absatz angegeben habe, keinen Ausweg gibt. –

+0

Ja, du hast Recht @Perry. Tatsächlich ist mein Kommentar "Lembda-Ausdruck ist eine Möglichkeit, auf eine zu delegierende Funktion zu verweisen" mit dem Verweis auf Ihre obige Antwort. Ich gehe das Konzept, das Sie dafür gegeben haben, dafür. – Lali

Verwandte Themen