【问题标题】:Cast dynamic to var将动态转换为 var
【发布时间】:2012-11-07 08:32:31
【问题描述】:

我有以下代码:

public class Processor
{
    private Query _query = 
        new SpecificQuery1();
    //OR
      //new SpecificQuery2();

   public void ProcessItem(dynamic dynamicResult)
   {
        //Can't use intellisense on dynamicResult

        var staticResult = dynamicResult as _query.GetSomeType();//Can't do it :(

        //Can use intellisense on staticResult
   }
}

而且,令人惊讶的是,它无法编译。有什么办法可以将动态转换为var?我知道这听起来很疯狂,但这部分将被大量编辑,如果有人更改 QueryImplementation,他还必须更改 ProcessItem() 中的类型。我想将步骤数减少到 1 - 只需替换 SpecificQuery() ,类型就会自行更改。

所以让我换个说法。我想知道是否有某种方法可以根据将哪个构造函数分配给基类 Query 来在 dynamicResult(或其中一些强制转换)上使用智能感知。

谢谢

编辑: 对不起,我可能问错了。我明白什么是动态和可变的。 我不打算在动态上使用智能感知。 我并不打算真正将动态转换为 var。

我想说的是,如果我在编译时知道动态将是什么类型(它存储在 Query 实现中 - 它可以是静态的,我想要的任何 const ) - 有什么办法可以吗?使用这些知识在 ProcessItem() 中启用智能感知?

【问题讨论】:

  • 您应该阅读一些内容以了解 var 和 dynamic 之间的区别。
  • 不,动态类型不能以您想要的方式与 Intellisense 一起使用,因为它们的属性/方法只有在运行时才能知道。您不能以这种方式转换为“var”。这真的很疯狂......但你可以这样做:“var staticResult = (SpecificQuery1)dynamicResult;”(请注意,你试图再次转换为未知类型,在运行时解决...)
  • 只是为了澄清。我明白两者之间的区别。我知道我不能在动态上使用智能——我知道为什么。我总是会在编译时知道,ProcessItem 中将使用什么类型,所以我认为可能有一些方法。
  • I will know always,那为什么是dynamic
  • 你上面的as 没有意义。强制转换将 compile-time 类型更改为必须知道编译时的特定类型。例如,如果你说var resultCast = resultOrig as string;,那么在那之后(以及null 检查)你可以说resultCast.Length 这样的东西,因为resultCast 的编译时类型是string,并且字符串有长度。但是,强制转换并没有改变只有一个对象的事实,并且该对象只有一种运行时类型。 Object.RefereceEquals(resultOrig, resultCast)。编译器怎么知道_query.GetSomeType() 会返回什么?

标签: c# .net dynamic casting var


【解决方案1】:

var 上下文关键字只是语法糖。不需要向它“强制转换”任何东西,因为用它声明的变量已经是强类型的。

如果函数结果的类型是dynamic,那么用var声明的变量也是。

staticResultdynamic 类型:

var staticResult = dynamicResult;

您无法在 dynamic 类型上获得智能感知。如果您知道您将获得的类型,然后强制转换为它 - 这将使您能够访问智能感知。

var staticResult = (myType)dynamicResult;

请注意,上面很容易导致运行时错误和异常导致进程崩溃。

【讨论】:

    【解决方案2】:

    请参阅this SO answer,它详细解释了vardynamic 之间的区别,根据您的问题,您应该知道编译器会在编译时知道var 的类型,而dynamic 只能在运行时确定;因此,您不能将从dynamic(在运行时确定)转换为var(在编译时确定)分配类型。

    那么,为什么不让它保持动态呢?

    【讨论】:

      【解决方案3】:

      不,你不能这样做。

      首先,您不能将某些内容强制转换为 var,因为 var 不是类型。此外,只能对静态已知的类型进行强制转换;这意味着您要转换的类型必须是硬编码的,并且不能是评估表达式的结果(例如您的示例中的方法调用 _query.GetSomeType())。

      【讨论】:

        【解决方案4】:

        你可以实现类似的东西

        public abstract class AbstractQuery
        {
             AbstractQuery Create(dynamic result);
        }
        public class SpecificQuery1 : AbstractQuery
        {
            new public SpecificQuery1 Create(dynamic result)
            {
               ...
            }
        }
        
        public void ProcessItem(dynamic dynamicResult)
        {
            var staticResult = _query.Create(dynamicResult);
        }
        

        从动态转换为类型化结果

        【讨论】:

        • 那么 Create() 方法的内容是什么?
        • 你的具体实现。动态结果从何而来?如果它是数据库查询的结果,您可以考虑使用 ORM 工具来获取具体实现而不是动态结果。
        猜你喜欢
        • 2021-11-19
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2013-05-14
        • 2013-02-27
        • 2013-12-15
        • 2012-05-15
        • 1970-01-01
        相关资源
        最近更新 更多