我有一堆代码有很多不同含义的整数(我更倾向于一般解决方案,但是对于一个具体的例子:每月的一个月与一年中的一个月对比等等)。我希望能够根据这些含义重载类构造函数。
例如
int a; // takes role A
int b; // takes role B
var A = new Foo(a); // should call one constructor
var B = new Foo(b); // should call another constructor
现在很明显,这不起作用,但如果我可以定义一个类型(不仅仅是一个别名),而是int
,除了这个名字之外:
typedef int TypeA; // stealing the C syntax
typedef int TypeB;
我可以做我需要的重载,让类型系统跟踪什么是什么。 特别是这将允许我确保值不会混淆,例如,作为一年的函数返回的值不会用作月中的日期。
在c#中,有没有class
或struct
包装器这么做?
如果解决方案也适用于花车和双打,那将是很好的。
答案 0 :(得分:13)
没有直接的typedef等效项,但您可以执行以下操作:
using TypeA = int;
using TypeB = int;
但是,这只是对类型进行别名而不是创建新的强类型。因此,在解析方法调用时,编译器仍会将它们视为int
。
更好的解决方案可能是创建包装int
的简单包装类并提供隐式转换,例如:
struct TypeA
{
public TypeA(int value)
{
this.realValue = value;
}
private int realValue;
public static implicit operator int(TypeA value)
{
return this.realValue;
}
public static implicit operator TypeA(int value)
{
return new TypeA(value);
}
}
但是,在大多数情况下,enum
会更合适。
答案 1 :(得分:6)
这可能是关闭的,但你不能使用枚举吗?枚举基数是int,但是是键入的,你可以根据传递的枚举类型定义不同的构造函数。
答案 2 :(得分:2)
如果仅仅是构造函数,你不能使用这样的东西:
int dom = 5;
int doy = 100;
Foo b = Foo.NewFromDayoftheMonth(dom);
Foo c = Foo.NewFromDayoftheYear(doy);
其中每个方法都是静态的,并根据传入的参数创建一个新的Foo对象。
对我来说这似乎是一个解决方案,其中没有其他的一个。
答案 3 :(得分:0)
我还会围绕值创建一个结构:
public struct TypeA
{
private int value;
public TypeA(int value)
{
this.value = value;
}
public static explicit operator int(TypeA a)
{
return a.value;
}
public static explicit operator TypeA(int value)
{
return new TypeA(value);
}
}
您还可以声明运算符组合类型和方法,以便在int值周围提供丰富的类型。
年份类型可以提供IsLeap
属性,月份中的某一天可以限制在1到31之间的值,并提供特殊算术。