现在我们有两个结构代表2d点.
public struct Point2D
{
public double X { get; set; }
public double Y { get; set; }
}
public struct Point2DF
{
public float X { get; set; }
public float Y { get; set; }
}
Run Code Online (Sandbox Code Playgroud)
现在我们需要创建另一个结构来代表整数的2d点.
public struct Point2DI
{
public int X { get; set; }
public int Y { get; set; }
}
Run Code Online (Sandbox Code Playgroud)
我的问题是我应该在这里使用泛型吗?如果我使用泛型,我会有一个结构而不是三个.
public struct Point<T>
{
public T X { get; set; }
public T Y { get; set; }
}
Run Code Online (Sandbox Code Playgroud)
但是消费者可以将T设置为字符串或某些类/结构.我该怎么办?有什么方法可以强制T为double/int/float吗?
我认为最好去Generics,因为这样会更清洁,因为你不需要多个类,继承或任何其他花哨的东西(也可以工作,但IMO它不会那么干净)
不幸的是,数字类型没有约束,所以这就是我提出的最接近的IMO:
public class Point<T>
where T : struct, IComparable, IFormattable, IConvertible, IComparable<T>, IEquatable<T>
{
protected readonly Type[] AllowedTypes =
{
typeof(decimal), typeof(double), typeof(short), typeof(int), typeof(long),
typeof(sbyte), typeof(float), typeof(ushort), typeof(uint), typeof(ulong)
};
public Point()
{
if (!this.AllowedTypes.Contains(typeof(T)))
{
throw new NotSupportedException(typeof(T).ToString());
}
}
public T X { get; set; }
public T Y { get; set; }
// UPDATE: arithmetic operations require dynamic proxy-Properties or
// variables since T is not explicitly numeric... :(
public T CalculateXMinusY()
{
dynamic x = this.X;
dynamic y = this.Y;
return x - y;
}
}
Run Code Online (Sandbox Code Playgroud)
它给你最大.智能感知支持,同时建议主要有效输入,但在使用不当时仍然失败.所有这些只使用一个,干净,可读,因此可维护的类.
唯一有点丑陋的是,这是一个巨大的泛型Type-Constraint,但这就是C#中所有数字类型的共同点,所以最好这样做.