开发者

Overriding a referenced assembly's class

开发者 https://www.devze.com 2023-03-07 11:47 出处:网络
I have assembly A, A has two classes a and b. A.a uses A.b in some of it\'s methods. In my assembly, B, I have two cl开发者_开发技巧asses B.a and B.b.

I have assembly A, A has two classes a and b.

A.a uses A.b in some of it's methods.

In my assembly, B, I have two cl开发者_开发技巧asses B.a and B.b.

B.a inherits from A.a and B.b inherits from A.b.

How would I get B.a to use B.b instead of A.b in the methods that use A.b, without having access to the source code?


Without having the source code for A, and that A doesn't do anything fancy like use IoC to resolve A.b, you can't. The dependency between A.a and A.b is set at compile time, and there is probably no easy way to intercept that.

If the methods from A.a that use A.b are virtual, then you can override them, and reproduce their functionality using B.b instead.


Without support from A.a? Nothing besides hackery decompilation to IL (ildasm), changing and then recompilation (ilasm). Which won't work if assembly A has a strong name (signed)


Well, there's two problems here.

First you should make the methods in A.a that you intend to use from A.b (and thus "replace" in B.b) virtual. This ensures that you can override them in B.b.

However, either A.a accesses A.b through static methods (which can't be overridden), or through an instance of A.b (which you can't easily replace.)

What you need to do in addition to making the methods virtual, as mentioned above, is to also provide a factory method inside A.a that creates an instance of A.b, and then you use the result of that, and then in B.a you override this method.

Let me demonstrate with this LINQPad program:

void Main()
{
    Ba instance = new Ba();
    instance.UseB();
}

public class Aa
{
    public void UseB()
    {
        Ab instance = CreateB();   // <-- call factory method instead of new
        instance.Test();
    }

    public virtual Ab CreateB()
    {
        return new Ab();
    }
}

public class Ab
{
    public virtual void Test()
    {
        Debug.WriteLine("A.b.Test");
    }
}

public class Ba : Aa
{
    public override Ab CreateB()   // <-- it still returns type "Ab"
    {
        return new Bb();           // <-- just create an instance of Bb instead
    }
}

public class Bb : Ab
{
    public override void Test()
    {
        Debug.WriteLine("B.b.Test");
    }
}


The methods in A would need to be marked as virtual in order for you to then be able to override them.

0

精彩评论

暂无评论...
验证码 换一张
取 消