2014-10-17 93 views
1

我想創建我自己的DataType,調用positiveInteger你如何創建你自己的數據類型?

我知道你在想什麼嗎?

您正在考慮在這裏使用uint。 但uint包含0,我只想要正數。

現在您可以告訴我,創建一個名爲positiveInteger的類。 是的,我可以創建一個名爲positiveIntegerClass,但我不知道如何實現該類,以便這個新的DataType只接受正整數值?

+1

應該發生什麼?拋出一個異常,默默地增加到1,... – LionAM 2014-10-17 20:57:18

+0

最有可能我想拋出一個異常 – Vishal 2014-10-17 20:58:02

+0

對於這樣的事情考慮一個'struct'而不是一個類。 – 2014-10-17 20:59:09

回答

4

一個例子imlementation可能是:

public struct PositiveInteger : IEquatable<PositiveInteger>, IComparable<PositiveInteger> 
{ 
    public PositiveInteger(uint value) 
    { 
     if (value <= 0) throw new ArgumentOutOfRangeException(); 
     _value = value; 
    } 

    public uint Value { get { return _value == 0 ? 1 : _value; } } 
    private readonly uint _value; 

    public static implicit operator PositiveInteger(uint value) 
    { 
     return new PositiveInteger(value); 
    } 

    public static implicit operator uint(PositiveInteger value) 
    { 
     return value.Value; 
    } 

    public static PositiveInteger operator +(PositiveInteger value1, PositiveInteger value2) 
    { 
     var result = value1.Value + value2.Value; 
     if (result < value1.Value || result < value2.Value) 
     { 
      throw new ArgumentOutOfRangeException(); //overflow 
     } 
     return result; 
    } 

    public static PositiveInteger operator -(PositiveInteger value1, PositiveInteger value2) 
    { 
     if (value1.Value < value2.Value) throw new ArgumentOutOfRangeException(); 
     return value1.Value - value2.Value; 
    } 

    public override bool Equals(object obj) 
    { 
     if (obj is PositiveInteger == false) return false; 
     return Equals((PositiveInteger)obj); 
    } 

    public bool Equals(PositiveInteger other) 
    { 
     return Value == other.Value; 
    } 

    public override int GetHashCode() 
    { 
     return (int)Value; 
    } 

    public int CompareTo(PositiveInteger other) 
    { 
     if (Value == other.Value) return 0; 
     return Value < other.Value ? -1 : 1; 
    } 

    public override string ToString() 
    { 
     return Value.ToString(CultureInfo.InvariantCulture); 
    } 
} 

和一個小測試:如果你試圖輸入0到你的數據類型

void Test() 
{ 
    var list = new List<PositiveInteger> {5, 1, 3}; 
    list.Sort(); // 1,3,5 

    var a = new PositiveInteger(1); 
    var b = new PositiveInteger(2); 

    var c = a + b; // = 3 
    var d = c - b; // = 1 
    var e = d - a; // throws ArgumentOutOfRangeException 
} 
+0

我所做的唯一改變就是讓它在內部存儲'uint'而不是'int'。但是,如果你這樣做,你可能需要顯式['檢查'](http://msdn.microsoft.com/en-us/library/74b4xzyw.aspx)。處理'a - c'案件。 – 2014-10-17 21:13:13

+0

這是一個好主意。 – LionAM 2014-10-17 21:13:58

+0

@Aarvol給出了一個很好的答案,但你的答案更有價值。 – Vishal 2014-10-17 21:18:09

5

如果你希望能夠「接受」編譯恆定int值的值,這是(mostly),那麼你就需要從int

public class positiveInteger 
{ 
    public static implicit operator positiveInteger(int source) 
    { 
     if(source <= 0) throw new ArgumentOutOfRangeException(); 
    } 
} 

這將實現一個implicit轉換爲positiveInteger允許您分配一個positiveInteger像這樣

positiveInteger number = 5; 

這將也,然而,使人們有可能分配一個int

int i = 5; 
positiveInteger number = i; // This will throw an exception when i <= 0 
+0

感謝您的好評!!!!!!! – Vishal 2014-10-17 21:02:33

+1

重要注意事項,這會比'int'在將函數傳遞給函數時表現得非常不同,因爲它不是結構類。 – 2014-10-17 21:09:36

1

試試你的構造函數。但它仍然不是一個好主意,因爲在使用它之前,您仍然應該驗證所有數據。就像在盲目分割之前檢查分母不爲零一樣。

public class PositiveInteger { 
    private uint _value; 

    public PositiveInteger(int x) { 
     if (x < 1) { 
      throw new Exception("Invalid value. Value is not positive."); 
     } 
     _value = x; 
    } 
}