Pyg*_*gmy 7 c# generics floating-point double int
我正在使用WPF扩展工具包(http://wpftoolkit.codeplex.com/).
它有一个很好的NumericUpDown控件,我想使用它,但在内部它使用双精度 - 这意味着它使用double.MinValue和double.MaxValue.
我想使用相同的控件,但我需要一个通用版本 - 对于int它需要使用int.MaxValue/MinValue,浮动float.MaxValue/MinValue等(我想你明白:))
所以我想将NumericUpDown复制到GNumericUpDown,其中T将是Type ..但这不起作用,因为泛型Type没有MinValue/MaxValue.通常我会使用'where'子句来指定基类型,但是这不能用作afaik,没有定义'MinValue'和'MaxValue'的通用接口.
有没有办法用泛型来解决这个问题,还是我真的需要复制/粘贴/搜索并替换每种类型的原始NumericUpDown?
好吧,既然你可以在执行时类型得到,你可以依靠的事实,所有的数字类型在.NET中有MinValue
和MaxValue
领域,并与反思阅读.它不会非常好,但很容易做到:
using System;
using System.Reflection;
// Use constraints which at least make it *slightly* hard to use
// with the wrong types...
public class NumericUpDown<T> where T : struct,
IComparable<T>, IEquatable<T>, IConvertible
{
public static readonly T MaxValue = ReadStaticField("MaxValue");
public static readonly T MinValue = ReadStaticField("MinValue");
private static T ReadStaticField(string name)
{
FieldInfo field = typeof(T).GetField(name,
BindingFlags.Public | BindingFlags.Static);
if (field == null)
{
// There's no TypeArgumentException, unfortunately. You might want
// to create one :)
throw new InvalidOperationException
("Invalid type argument for NumericUpDown<T>: " +
typeof(T).Name);
}
return (T) field.GetValue(null);
}
}
class Test
{
static void Main()
{
Console.WriteLine(NumericUpDown<int>.MaxValue);
Console.WriteLine(NumericUpDown<float>.MinValue);
}
}
Run Code Online (Sandbox Code Playgroud)
请注意,如果您使用不合适的类型,我试图尽可能强制编译时错误...但它不会万无一失.如果您设法找到具有所有正确接口但没有MinValue
和MaxValue
字段的结构,那么任何使用该NumericUpDown
类型的尝试都将导致抛出异常.
OP对另一个答案做出了评论:
我想在我的XAML中使用这些控件.我的想法是创建一个通用版本,然后创建像NumericUpDownInt这样的空类:GNumericUpDown {}这将是要走的路,还是有更好/更清洁的方式来获取你的知识
如果您要去那条路线,那么直接通过最小值和最大值:
class abstract GenericNumericUpDown<T>
{
public GenericNumericUpDown(T min, T max) { ... }
}
class NumericUpDownInt : GenericNumericUpDown<int>
{
public NumericUpDownInt() : base(int.MinValue, int.MaxValue) { ... }
}
class NumericUpDownFloat : GenericNumericUpDown<float>
{
public NumericUpDownFloat() : base(float.MinValue, float.MaxValue) { ... }
}
class NumericUpDownDouble : GenericNumericUpDown<double>
{
public NumericUpDownDouble() : base(double.MinValue, double.MaxValue) { ... }
}
Run Code Online (Sandbox Code Playgroud)