使用其他类常量值调用构造函数

时间:2016-07-27 18:52:16

标签: c# .net-4.6

我希望构造函数调用只允许有限范围的"扩展"。让我们说我有这两个类:

public class Foo
{
    public Foo(Extension ext) 
    { 
        // do something
    }
}

public class Extension
{
    public const string TXT = ".txt";
    public const string XML = ".xml";
}

因此,当另一位开发人员想要使用Foo时,他只能使用Extension类中的值来执行此操作:

Foo foo = new Foo(Extension.TXT);

但是当我尝试这样做时,我收到一个IDE错误:"cannot convert from 'string' to '<ProjectName>.Extension'

作为&#34;解决方法&#34;我可以将我的Extension课程更改为:

public class Extension
{
    public enum File
    {
        TXT,
        XML
    }
}

并像这样使用它:

Foo foo = new Foo(Extension.File.TXT);

效果非常好,但我不喜欢的是调用时间更长(class - &gt; enum - &gt;元素而不是class - &gt;元素)。

所以,问题是我的解决方法实际上是唯一有效,正确或最佳实践的解决方案吗?

5 个答案:

答案 0 :(得分:5)

您可以使用 Java样式枚举

public class Extension
{
    string _Extension = null;

    private Extension(string ext)
    {
        _Extension = ext;
    }

    public static Extension TXT 
    {
        get {  return new Extension(".txt"); }
    }

    public static Extension XML
    {
        get { return new Extension(".xml"); }
    }

    public override string ToString()
    {
        return _Extension;
    }

    public override bool Equals(object obj)
    {
        var e = obj as Extension;
        if (e == null) return false;

        return e._Extension == this._Extension;
    }

    public override int GetHashCode()
    {
        return _Extension.GetHashCode();
    }
}

答案 1 :(得分:3)

第一个示例将Extension用作具有几个字符串常量的类。第二个例子使用枚举来代替常量。

public class Foo
{
    // this .ctor expects a type of Extension, not a string.
    public Foo(Extension ext) 
    { 
        // do something
    }
}

// This class has only constant string values.
public class Extension
{
    public const string TXT = ".txt";
    public const string XML = ".xml";
}

尝试将字符串传递给上面的.ctor将无法正常工作,因为它需要Extension类型,而不是字符串。

// this passes in a string, not a type.
Foo foo = new Foo(Extension.TXT);

由于您希望限制Foo .ctor可用的值,请使用您在第二个示例中使用的枚举:

public class Foo
{
    public Foo(File ext) 
    { 
        // do something
    }
}

public enum File
{
    TXT,
    XML
}

然后这将按预期工作:

Foo foo = new Foo(File.TXT);

答案 2 :(得分:1)

为什么不在类Foo之外声明枚举并且没有像扩展名这样的特殊类?

public enum Extension
{
    TXT,
    XML
}

public class Foo 
{
    public Foo(Extension ext) 
    {
        // do something
    }
}

然后,在构建Foo对象时,您可以执行以下操作:

Foo foo = new Foo(Extension.TXT);

答案 3 :(得分:0)

您可以为字符串定义默认构造函数和隐式运算符。例如。类似的东西:

public class Extension
{
    public const string TXT = ".txt";
    public const string XML = ".xml";

    private _value;
    public Extension(string value){if(value == TXT || value == XML) _value = value; else throw new NotImplementedException();}
    public static implicit operator string(Extension value){return _value;}
    public static implicit operator Extension(string value){if(value == TXT || value == XML) _value = value; else throw new NotImplementedException();}
}

你可以这样调用Foo(&#34; .txt&#34;)或Foo(Extension.TXT)

或者您可以将TXT定义为Extension的实例:

public class Extension
{
    public const Extension TXT = new Extension(".txt");
    public const Extension XML = new Extension(".xml");

    public Value{get;private set;}
    public Extension(string value){Value = value;}
 }

答案 4 :(得分:0)

只需将Extesion的第一个声明从Class更改为Enum