Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/unit-testing/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# c语言中的拦截方法/属性调用#_C#_Unit Testing_Reflection - Fatal编程技术网

C# c语言中的拦截方法/属性调用#

C# c语言中的拦截方法/属性调用#,c#,unit-testing,reflection,C#,Unit Testing,Reflection,在下面的代码中,我有一个由main方法调用的类Foo(没有接口)。属性没有支持字段或setter,而是调用私有方法。Foo不能更改,Foo的用法也不能更改为IFoo接口 -如何更改foo.FooValue的值? -在System.Reflection、System.Reflection.Emit、.NET标准库等(不安全代码等)中是否有我可以包含在单元测试中以更改返回值的内容? 我很感激如果有什么东西注定是非常“邪恶”的,但我对“邪恶”的答案感兴趣 相关问题: -也许答案是“不”,但我不相信上面

在下面的代码中,我有一个由main方法调用的类Foo(没有接口)。属性没有支持字段或setter,而是调用私有方法。Foo不能更改,Foo的用法也不能更改为IFoo接口

-如何更改foo.FooValue的值?

-在System.Reflection、System.Reflection.Emit、.NET标准库等(不安全代码等)中是否有我可以包含在单元测试中以更改返回值的内容?

我很感激如果有什么东西注定是非常“邪恶”的,但我对“邪恶”的答案感兴趣

相关问题:

-也许答案是“不”,但我不相信上面的答案,因为上面的答案只是指出,你无法通过更改(不存在的)支持字段来实现这一点

-有趣。不确定这是否是我的答案,如果是,不确定如何在单元测试中使用它


编辑:好的。我将重新编写代码,使其更易于测试。然而,出于兴趣,有没有人成功地通过黑客破解了这种情况?

您可以为
Foo
创建一个可以模拟的代理:

public class FooProxy : IFoo
{
    private Foo _Foo;
    public FooProxy(Foo foo)
    {
        _Foo = foo;
    }
    public int FooValue
    {
        get {return _Foo.FooValue();
    }
}

public interface IFoo
{
    public int FooValue {get;}
}

然后,您可以使用DI“注入”一个
IFoo
,使您的代码更易于测试。

您可以为
Foo
创建一个可以模拟的代理:

public class FooProxy : IFoo
{
    private Foo _Foo;
    public FooProxy(Foo foo)
    {
        _Foo = foo;
    }
    public int FooValue
    {
        get {return _Foo.FooValue();
    }
}

public interface IFoo
{
    public int FooValue {get;}
}

然后,您可以使用DI“注入”一个
IFoo
,使您的代码更易于测试。

您可以为
Foo
创建一个可以模拟的代理:

public class FooProxy : IFoo
{
    private Foo _Foo;
    public FooProxy(Foo foo)
    {
        _Foo = foo;
    }
    public int FooValue
    {
        get {return _Foo.FooValue();
    }
}

public interface IFoo
{
    public int FooValue {get;}
}

然后,您可以使用DI“注入”一个
IFoo
,使您的代码更易于测试。

您可以为
Foo
创建一个可以模拟的代理:

public class FooProxy : IFoo
{
    private Foo _Foo;
    public FooProxy(Foo foo)
    {
        _Foo = foo;
    }
    public int FooValue
    {
        get {return _Foo.FooValue();
    }
}

public interface IFoo
{
    public int FooValue {get;}
}


然后您可以使用DI“注入”一个
IFoo
,使您的代码更易于测试。

您拥有
Foo
类吗?您将其硬编码为返回0。添加一个属性或字段,然后让它返回属性并添加一个setter。那么您的兴趣仅仅是单元测试?你实际上是想通过改变Foo的行为来“模仿”
Foo
。我宁愿不重构,如果我要重构的话,我会通过使用at作为IFoo将Foo与代码分离。@DStanley基本上是的。我的三个步骤是:我可以模拟它(否),我可以反映它(否),让我们来看看实现。你想测试
FooValue
的值还是依赖于
FooValue
的其他东西?你拥有
Foo
类吗?您将其硬编码为返回0。添加一个属性或字段,然后让它返回属性并添加一个setter。那么您的兴趣仅仅是单元测试?你实际上是想通过改变Foo的行为来“模仿”
Foo
。我宁愿不重构,如果我要重构的话,我会通过使用at作为IFoo将Foo与代码分离。@DStanley基本上是的。我的三个步骤是:我可以模拟它(否),我可以反映它(否),让我们来看看实现。你想测试
FooValue
的值还是依赖于
FooValue
的其他东西?你拥有
Foo
类吗?您将其硬编码为返回0。添加一个属性或字段,然后让它返回属性并添加一个setter。那么您的兴趣仅仅是单元测试?你实际上是想通过改变Foo的行为来“模仿”
Foo
。我宁愿不重构,如果我要重构的话,我会通过使用at作为IFoo将Foo与代码分离。@DStanley基本上是的。我的三个步骤是:我可以模拟它(否),我可以反映它(否),让我们来看看实现。你想测试
FooValue
的值还是依赖于
FooValue
的其他东西?你拥有
Foo
类吗?您将其硬编码为返回0。添加一个属性或字段,然后让它返回属性并添加一个setter。那么您的兴趣仅仅是单元测试?你实际上是想通过改变Foo的行为来“模仿”
Foo
。我宁愿不重构,如果我要重构的话,我会通过使用at作为IFoo将Foo与代码分离。@DStanley基本上是的。我的三个步骤是:我可以模拟它(否),我可以反映它(否),让我们来看看实现。你想测试
FooValue
的值还是取决于
FooValue
的其他值?谢谢你的回答。我知道如果我的代码使用接口,它将更易于测试。一般来说,dto并不是这样(foo是一种dto,有人对它的实现有点热情)。如果我这样做了,我可能只会使用Moq而不是代理。因此,您对我的问题的回答是:“您的代码是不稳定的,在重构之外没有模仿Foo的技巧”@NathanCooper-我喜欢您旋转答案的方式:)-在.Net中没有任何轻量级的东西可以处理对非虚拟/非接口方法的拦截调用。某种形式的IL重写是可以实现这一点的最高抽象层,使用调试接口或自定义JIT/运行时是下一步…@Nathan你的程序与
Foo
紧密耦合-如果你需要用
Foo
以外的东西测试你的方法,正确的方法是打破紧密耦合。可能有低级的方法(IL重写等),但它们只是绕过了真正的问题。谢谢你的回答。我知道如果我的代码使用接口,它将更易于测试。一般来说,dto并不是这样(foo是一种dto,有人对它的实现有点热情)。如果我这样做了,我可能只会使用Moq而不是代理。所以你对我的问题的回答是:“你的代码是不稳定的,在重构之外没有模仿Foo的技巧”@NathanCooper-我喜欢你旋转答案的方式:)-在.Net中没有什么轻量级的东西可以用来拦截对非病毒的调用