简体   繁体   English

如何将垫片浇铸成混凝土型?

[英]How to cast shim as concrete type?

I have a shim based on ClassA.PropertyB, where PropertyB is of type ClassB. 我有一个基于ClassA.PropertyB的垫片,其中PropertyB是ClassB类型。 ClassA is internal and lives in another assembly from my test project. ClassA是内部的,位于我的测试项目的另一个程序集中。 I've added a reference in the AssemblyInfo.cs so this internal can be seen by my test project and I'm able to create the shim. 我在AssemblyInfo.cs中添加了一个引用,以便可以在我的测试项目中看到此内部,并且能够创建垫片。

I'd like to send the shimClassB instance into ClassA via the constructor: 我想通过构造函数将shimClassB实例发送到ClassA中:

public ClassA(object someInstance)
{
  PropertyB = (ClassB)someInstance;
} 

The above throws an InvalidCastException: 上面抛出一个InvalidCastException:

Unable to cast object of type shimClassB to type ClassB.

Is there some other technique that will get the shim instance into ClassA? 还有其他一些技术可以将Shim实例放入ClassA吗?

It is important to note that ClassB and ShimClassB do not have a base class-derived class relationship. 必须注意, ClassBShimClassB没有基类派生的类关系。 So the casts you are doing, might not be doing quite what you expect. 因此,您正在执行的演员表可能未达到预期的效果。 You are seeing implicit conversions working due to user-defined conversions that Microsoft.Fakes have provided for you. 由于Microsoft.Fakes为您提供的用户定义的转换,您看到隐式转换有效。

Your ShimClassB inherits from ShimBase<T> , where T is ClassB . 您的ShimClassB继承自ShimBase<T> ,其中T是ClassB This class has a method that introduces a user-defined implicit conversion between ShimClassB and ClassB . 此类具有一种在ShimClassBClassB之间引入用户定义的隐式转换的方法。

public static implicit operator T(ShimBase<T> shim)

When you attempt to do. 当您尝试做时。

public ClassA(object someInstance)
{
    PropertyB = (ClassB)someInstance;
} 

you cannot have a cast to ClassB as there is no conversion defined between object and ClassB . 您不能ClassB转换为ClassB因为objectClassB之间没有定义转换。

From the C# Programming language specification 6.2.4 Explicit reference conversions: 从C#编程语言规范6.2.4显式引用转换:

For an explicit reference conversion to succeed at run-time, the value of the source operand must be null, or the actual type of the object referenced by the source operand must be a type that can be converted to the destination type by an implicit reference conversion (§6.1.6) or boxing conversion (§6.1.7). 为了在运行时成功进行显式引用转换,源操作数的值必须为null,或者源操作数引用的对象的实际类型必须是可以通过隐式引用转换为目标类型的类型。转换(§6.1.6)或拳击转换(§6.1.7)。 If an explicit reference conversion fails, a System.InvalidCastException is thrown. 如果显式引用转换失败,则将引发System.InvalidCastException。

You would find if your code had an intermediary cast it would no longer throw an InvalidCastException however this is not a final solution as you don't want a cast to the Shim in your constructor: 您会发现,如果您的代码具有中间类型InvalidCastException ,它将不再抛出InvalidCastException但这不是最终的解决方案,因为您不希望在构造函数中转换为Shim:

public ClassA(object someInstance)
{
    PropertyB = (ClassB)(ShimClassB)someInstance;
} 

To solve this issue. 解决这个问题。 I would advise changing your ClassA constructor so that it is typed and not accepting object , when you pass your shimClassB into this constructor you will find the user-defined implicit conversion will be used: 我建议更改您的ClassA构造函数,使其被键入并且不接受object ,当您将shimClassB传递给该构造函数时,您会发现将使用用户定义的隐式转换:

// The user-defined implicit conversion takes care of this for us
ClassA(shimClassB); 

public ClassA(ClassB someInstance)
{
  PropertyB = someInstance;
} 

or if you want to keep your constructor as it is: 或者如果您想保持构造函数不变:

ClassA((ClassB)shimClassB); 

public ClassA(object someInstance)
{
  PropertyB = (ClassB)someInstance;
} 

I do not see any issues with doing that. 我认为这样做没有任何问题。 Please verify that your property is of the correct type or try to assign some ShimClassB object to a new variable of type ClassB. 请验证您的属性的类型正确,或尝试将一些ShimClassB对象分配给ClassB类型的新变量。

It might be helpful to show us your code, even though I just tried exact the same example without getting any exceptions. 尽管我只是尝试了完全相同的示例而没有遇到任何异常,但向我们展示您的代码可能会有所帮助。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM