下面的结构,为什么Default = new NullableChar();???没有这样的构造函数啊,构造函数不是带参数了么?请高手指教,Default的值会是多少?
using System;namespace Nullables
{
public interface INullableType
{
object Value { get; }
bool HasValue { get; }
} [System.ComponentModel.TypeConverter(typeof(Nullables.TypeConverters.NullableCharConverter)), Serializable()]
public struct NullableChar : INullableType, IComparable
{
public static readonly NullableChar Default = new NullableChar(); Char _value;
bool hasValue; #region Constructors public NullableChar(Char value)
{
_value = value;
hasValue = true;
} #endregion #region INullable Members object INullableType.Value
{
get { return Value; }
} public bool HasValue
{
get { return hasValue; }
} #endregion public Char Value
{
get
{
if (hasValue)
return _value;
else
throw new InvalidOperationException("Nullable type must have a value.");
}
} #region Casts public static explicit operator Char(NullableChar nullable)
{
if (!nullable.HasValue)
throw new NullReferenceException(); return nullable.Value;
} public static implicit operator NullableChar(Char value)
{
return new NullableChar(value);
} public static implicit operator NullableChar(DBNull value)
{
return NullableChar.Default;
} #endregion public override string ToString()
{
if (HasValue)
return Value.ToString();
else
return string.Empty;
} public override bool Equals(object obj)
{
if (obj is DBNull && !HasValue)
return true;
else if (obj is NullableChar)
return Equals((NullableChar)obj);
else
return false; //if this is reached, it is either some other type, or DBnull is compared with this and we have a Value.
} public bool Equals(NullableChar x)
{
return Equals(this, x);
} public static bool Equals(NullableChar x, NullableChar y)
{
if (x.HasValue != y.HasValue) //one is null
return false;
else if (x.HasValue) //therefor y also HasValue
return x.Value == y.Value;
else //both are null
return true;
} public static bool operator ==(NullableChar x, NullableChar y)
{
return x.Equals(y);
} public static bool operator ==(NullableChar x, object y)
{
return x.Equals(y);
} public static bool operator !=(NullableChar x, NullableChar y)
{
return !x.Equals(y);
} public static bool operator !=(NullableChar x, object y)
{
return !x.Equals(y);
} public static NullableInt32 operator +(NullableChar x, NullableChar y)
{
if (!x.HasValue || !y.HasValue) //one or both are null
return NullableInt32.Default; return new NullableInt32(x.Value + y.Value);
} public static NullableInt32 operator -(NullableChar x, NullableChar y)
{
if (!x.HasValue || !y.HasValue) //one or both are null
return NullableInt32.Default; return new NullableInt32(x.Value - y.Value);
} public static NullableInt32 operator *(NullableChar x, NullableChar y)
{
if (!x.HasValue || !y.HasValue) //one or both are null
return NullableInt32.Default; return new NullableInt32(x.Value * y.Value);
} public static NullableInt32 operator /(NullableChar x, NullableChar y)
{
if (!x.HasValue || !y.HasValue) //one or both are null
return NullableInt32.Default; return new NullableInt32(x.Value / y.Value);
}
public override int GetHashCode()
{
if (HasValue)
return Value.GetHashCode();
else
return 0; //GetHashCode() doesn't garantee uniqueness, and neither do we.
} #region IComparable Members public int CompareTo(object obj)
{
if (obj is NullableChar) //chack and unbox
{
NullableChar value = (NullableChar)obj; if (value.HasValue == this.HasValue) //both null or not null
{
if (this.HasValue) //this has a value, so they both do
return Value.CompareTo(value.Value);
else
return 0; //both null, so they are equal;
}
else //one is null
{
if (HasValue) //he have a value, so we are greater.
return 1;
else
return -1;
}
}
else if (obj is Char)
{
Char value = (Char)obj; if (HasValue) //not null, so compare the real values.
return Value.CompareTo(value);
else
return -1; //this is null, so less that the real value;
} throw new ArgumentException("NullableChar can only compare to another NullableChar or a System.Char");
} #endregion
}
}
using System;namespace Nullables
{
public interface INullableType
{
object Value { get; }
bool HasValue { get; }
} [System.ComponentModel.TypeConverter(typeof(Nullables.TypeConverters.NullableCharConverter)), Serializable()]
public struct NullableChar : INullableType, IComparable
{
public static readonly NullableChar Default = new NullableChar(); Char _value;
bool hasValue; #region Constructors public NullableChar(Char value)
{
_value = value;
hasValue = true;
} #endregion #region INullable Members object INullableType.Value
{
get { return Value; }
} public bool HasValue
{
get { return hasValue; }
} #endregion public Char Value
{
get
{
if (hasValue)
return _value;
else
throw new InvalidOperationException("Nullable type must have a value.");
}
} #region Casts public static explicit operator Char(NullableChar nullable)
{
if (!nullable.HasValue)
throw new NullReferenceException(); return nullable.Value;
} public static implicit operator NullableChar(Char value)
{
return new NullableChar(value);
} public static implicit operator NullableChar(DBNull value)
{
return NullableChar.Default;
} #endregion public override string ToString()
{
if (HasValue)
return Value.ToString();
else
return string.Empty;
} public override bool Equals(object obj)
{
if (obj is DBNull && !HasValue)
return true;
else if (obj is NullableChar)
return Equals((NullableChar)obj);
else
return false; //if this is reached, it is either some other type, or DBnull is compared with this and we have a Value.
} public bool Equals(NullableChar x)
{
return Equals(this, x);
} public static bool Equals(NullableChar x, NullableChar y)
{
if (x.HasValue != y.HasValue) //one is null
return false;
else if (x.HasValue) //therefor y also HasValue
return x.Value == y.Value;
else //both are null
return true;
} public static bool operator ==(NullableChar x, NullableChar y)
{
return x.Equals(y);
} public static bool operator ==(NullableChar x, object y)
{
return x.Equals(y);
} public static bool operator !=(NullableChar x, NullableChar y)
{
return !x.Equals(y);
} public static bool operator !=(NullableChar x, object y)
{
return !x.Equals(y);
} public static NullableInt32 operator +(NullableChar x, NullableChar y)
{
if (!x.HasValue || !y.HasValue) //one or both are null
return NullableInt32.Default; return new NullableInt32(x.Value + y.Value);
} public static NullableInt32 operator -(NullableChar x, NullableChar y)
{
if (!x.HasValue || !y.HasValue) //one or both are null
return NullableInt32.Default; return new NullableInt32(x.Value - y.Value);
} public static NullableInt32 operator *(NullableChar x, NullableChar y)
{
if (!x.HasValue || !y.HasValue) //one or both are null
return NullableInt32.Default; return new NullableInt32(x.Value * y.Value);
} public static NullableInt32 operator /(NullableChar x, NullableChar y)
{
if (!x.HasValue || !y.HasValue) //one or both are null
return NullableInt32.Default; return new NullableInt32(x.Value / y.Value);
}
public override int GetHashCode()
{
if (HasValue)
return Value.GetHashCode();
else
return 0; //GetHashCode() doesn't garantee uniqueness, and neither do we.
} #region IComparable Members public int CompareTo(object obj)
{
if (obj is NullableChar) //chack and unbox
{
NullableChar value = (NullableChar)obj; if (value.HasValue == this.HasValue) //both null or not null
{
if (this.HasValue) //this has a value, so they both do
return Value.CompareTo(value.Value);
else
return 0; //both null, so they are equal;
}
else //one is null
{
if (HasValue) //he have a value, so we are greater.
return 1;
else
return -1;
}
}
else if (obj is Char)
{
Char value = (Char)obj; if (HasValue) //not null, so compare the real values.
return Value.CompareTo(value);
else
return -1; //this is null, so less that the real value;
} throw new ArgumentException("NullableChar can only compare to another NullableChar or a System.Char");
} #endregion
}
}
如果一个类没有构造函数,系统会为你生成一个不带参数的默认构造函数
如果你定义了至少一个构造函数,系统就不会再自动生成了因此你可以把现有的构造函数删掉,或者加一个参数来调用Default = new NullableChar('?');
结构的话的确允许这样用,所有的成员都会被初始化成默认值,
Default = new NullableChar();
的效果跟
Default = new NullableChar((char)0);
是一样的
using System;namespace Nullables
{
[System.ComponentModel.TypeConverter(typeof(Nullables.TypeConverters.NullableDateTimeConverter)), Serializable()]
public struct NullableDateTime : INullableType, IFormattable, IComparable
{
public static readonly NullableDateTime Default = new NullableDateTime(); DateTime _value;
bool hasValue; #region Constructors public NullableDateTime(DateTime value)
{
_value = value;
hasValue = true;
} #endregion #region INullable Members object INullableType.Value
{
get { return Value; }
} public bool HasValue
{
get { return hasValue; }
} #endregion public DateTime Value
{
get
{
if (hasValue)
return _value;
else
throw new InvalidOperationException("Nullable type must have a value.");
}
} #region Casts public static explicit operator DateTime(NullableDateTime nullable)
{
if (!nullable.HasValue)
throw new NullReferenceException(); return nullable.Value;
} public static implicit operator NullableDateTime(DateTime value)
{
return new NullableDateTime(value);
} public static implicit operator NullableDateTime(DBNull value)
{
return NullableDateTime.Default;
} #endregion public override string ToString()
{
if (HasValue)
return Value.ToString();
else
return string.Empty;
} public override bool Equals(object obj)
{
if (obj is DBNull && !HasValue)
return true;
else if (obj is NullableDateTime)
return Equals((NullableDateTime)obj);
else
return false; //if this is reached, it is either some other type, or DBnull is compared with this and we have a Value.
} public bool Equals(NullableDateTime x)
{
return Equals(this, x);
} public static bool Equals(NullableDateTime x, NullableDateTime y)
{
if (x.HasValue != y.HasValue) //one is null
return false;
else if (x.HasValue) //therefor y also HasValue
return x.Value == y.Value;
else //both are null
return true;
} public static bool operator ==(NullableDateTime x, NullableDateTime y)
{
return x.Equals(y);
} public static bool operator ==(NullableDateTime x, object y)
{
return x.Equals(y);
} public static bool operator !=(NullableDateTime x, NullableDateTime y)
{
return !x.Equals(y);
} public static bool operator !=(NullableDateTime x, object y)
{
return !x.Equals(y);
}
public override int GetHashCode()
{
if (HasValue)
return Value.GetHashCode();
else
return 0; //GetHashCode() doesn't garantee uniqueness, and neither do we.
} //TODO: Operators for DateTime (?) #region IFormattable Members string System.IFormattable.ToString(string format, IFormatProvider formatProvider)
{
if (HasValue)
return Value.ToString(format, formatProvider);
else
return string.Empty;
} #endregion #region IComparable Members public int CompareTo(object obj)
{
if (obj is NullableDateTime) //chack and unbox
{
NullableDateTime value = (NullableDateTime)obj; if (value.HasValue == this.HasValue) //both null or not null
{
if (this.HasValue) //this has a value, so they both do
return Value.CompareTo(value.Value);
else
return 0; //both null, so they are equal;
}
else //one is null
{
if (HasValue) //he have a value, so we are greater.
return 1;
else
return -1;
}
}
else if (obj is DateTime)
{
DateTime value = (DateTime)obj; if (HasValue) //not null, so compare the real values.
return Value.CompareTo(value);
else
return -1; //this is null, so less that the real value;
} throw new ArgumentException("NullableDateTime can only compare to another NullableDateTime or a System.DateTime");
} #endregion
}
}
DateTime d = new DateTime();
Console.WriteLine(d);
输出:
0001-1-1 0:00:00