繁体   English   中英

泛型类型的隐式运算符

[英]implicit operator on generic types

使用如下所示的隐式运算符有什么问题吗:

//linqpad c# program example
void Main()
{
    var testObject = new MyClass<int>() { Value = 1 };

    var add = 10 + testObject; //implicit conversion to int here
    add.Dump(); // 11
}

class MyClass<T>
{
    public T Value { get; set; }
    public static implicit operator T (MyClass<T> myClassToConvert)
    {
        return myClassToConvert.Value;
    }
}

我想我可以用这种方式将对象的实例视为值类型,但是看到我从未见过这样的例子,我想也许有理由不做这样的事情,有人可以指出?

在我的实际代码中,我正在考虑将其作为数据抽象层的一部分,以便我可以返回带有描述底层数据的信息的对象,但允许逻辑代码在需要了解所有信息时将其视为值类型是值,同时使用泛型保持它的​​完整性和类型安全。

如果以下所有情况都为真:

  • MyClass<T>类型的所有可能值(如果它不是值类型,则包括null !)映射到T的有效值

  • 隐式运算符从不抛出(甚至对于null也不抛出!)

  • 隐式转换具有语义意义并且不会让客户端程序员感到困惑

那么这没有任何问题。 当然,你可以做这三件事中的任何一件,但这将是糟糕的设计。 特别是,抛出的隐式运算符可能很难调试,因为它被调用的地方并没有说它正在被调用。

例如,考虑T? 没有隐式转换为T (其中T是,当然,一个值类型)。 如果有这样一个隐式操作符,它会在T? 是 null,因为没有明显的值可以将null转换为对任何值类型T都有意义的值。


让我举一个例子,我在调试隐式运算符抛出的问题时遇到问题:

public string Foo()
{
    return some_condition ? GetSomething() : null;
}

在这里, GetSomething返回了我编写的某种类型的东西,它具有用户定义的到string隐式转换。 绝对确定GetSomething永远不会返回null ,但我得到了一个NullReferenceException 为什么? 因为上面的代码等价于

return some_condition ? (string)GetSomething() : (string)null;

但要

return (string)(some_condition ? GetSomething() : (Something)null);

现在您可以看到null来源了!

这是一个很棒的模式。 请记住,为了使用它作为类型的变量T ,你必须明确地将其转换为T ,或将其分配给类型的变量T 强制转换将在方法调用和其他采用T事情(例如您的加法示例)中自动发生。

没有赋值的隐式转换?

暂无
暂无

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

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