2011-08-03 6 views
0

G'Day,C# 사용자 정의 유형 선언 - 작동하지 않음

게시물의 길이에 사과드립니다 만, 코드가 필요합니다.

C#으로 직접 값 유형을 만들고 싶습니다. 나는 구조체 TCountryID을 구현하지만, 나는 다음과 같은 코드를 작성 후 다음과 같은 문제를 가지고 나는 아직도 뭔가를 놓친 거지 나타납니다 형식을 변환 할 수 없습니다)

int iTest = 0; 
    TCountryID tcidTest; 
    iTest = tcidTest; 

1 'MyNamespace.System.TCountryID' 'INT'

IConvertable 인터페이스를 구현하면이 문제를 해결할 수 있다고 생각했을까요?

2.1) 암시 'MyNameSpace.System.TCountryID' 2.2) 암시 적으로 변환 할 수 없습니다 유형 유형 'INT'을 변환 할 수 없습니다 나는 해결책을 달성 어떻게 'INT'

에 'MyNameSpace.System.TCountryID' 2.x 문제?

TIA

구조체 코드는 다음과 같습니다 :

문서에서
[Serializable] 
    [System.Runtime.InteropServices.ComVisible(true)] 
    public struct TCountryID : IFormattable, IConvertible, IComparable, IComparable<TCountryID>, IEquatable<TCountryID> 
    { 
     #region Private Members 
     private int FValue;      //Base type we are encapsulating 
     #endregion 

     #region Public Members 

     public override int GetHashCode() 
     { 
      return FValue; 
     } 

     #region IConvertible 
     public TypeCode GetTypeCode() 
     { 
      return TypeCode.Int32; 
     } 

     bool IConvertible.ToBoolean(IFormatProvider AProvider) 
     { 
      return System.Convert.ToBoolean(FValue); 
     } 

     byte IConvertible.ToByte(IFormatProvider AProvider) 
     { 
      return System.Convert.ToByte(FValue); 
     } 

     char IConvertible.ToChar(IFormatProvider AProvider) 
     { 
      return Convert.ToChar(FValue); 
     } 

     DateTime IConvertible.ToDateTime(IFormatProvider AProvider) 
     { 
      return System.Convert.ToDateTime(FValue); 
     } 

     decimal IConvertible.ToDecimal(IFormatProvider AProvider) 
     { 
      return System.Convert.ToDecimal(FValue); 
     } 

     double IConvertible.ToDouble(IFormatProvider AProvider) 
     { 
      return System.Convert.ToDouble(FValue); 
     } 

     short IConvertible.ToInt16(IFormatProvider AProvider) 
     { 
      return System.Convert.ToInt16(FValue); 
     } 

     int IConvertible.ToInt32(IFormatProvider AProvider) 
     { 
      return System.Convert.ToInt32(FValue) ; 
     } 

     long IConvertible.ToInt64(IFormatProvider AProvider) 
     { 
      return System.Convert.ToInt64(FValue); 
     } 

     sbyte IConvertible.ToSByte(IFormatProvider AProvider) 
     { 
      return System.Convert.ToSByte(FValue); 
     } 

     float IConvertible.ToSingle(IFormatProvider AProvider) 
     { 
      return System.Convert.ToSingle(FValue); 
     } 

     object IConvertible.ToType(Type ATargetType, IFormatProvider AProvider) 
     { 
      if (ATargetType == null) 
       throw new ArgumentNullException("ATargetType"); 

      return System.Convert.ChangeType(FValue, ATargetType, AProvider); 
     } 

     ushort IConvertible.ToUInt16(IFormatProvider AProvider) 
     { 
      return System.Convert.ToUInt16(FValue); 
     } 

     uint IConvertible.ToUInt32(IFormatProvider AProvider) 
     { 
      return System.Convert.ToUInt32(FValue); 
     } 

     ulong IConvertible.ToUInt64(IFormatProvider AProvider) 
     { 
      return System.Convert.ToUInt64(FValue); 
     } 

     #endregion 
     #region IComparable 
     public int CompareTo(object AValue) 
     { 
      TCountryID tcidTmp = (TCountryID)AValue; 

      if (AValue == null) 
       return 1; 

      if (!(AValue is System.Int32)) 
       throw new ArgumentException("Value is not a System.Int32"); 

      if (FValue == tcidTmp.FValue) 
       return 0; 

      if (FValue > tcidTmp.FValue) 
       return 1; 
      else 
       return -1; 
     } 

     public int CompareTo(TCountryID AValue) 
     { 
      if (FValue == AValue.FValue) 
       return 0; 

      if (FValue > AValue.FValue) 
       return 1; 
      else return -1; 
     } 
#endregion 
     #region IEquatable 
     public bool Equals(TCountryID obj) 
     { 
      return obj.FValue == FValue; 
     } 

     public override bool Equals(object obj) 
     { 
      if (!(obj is System.TCountryID)) 
       return false; 

      return ((TCountryID)obj).FValue == FValue; 
     } 
     #endregion 
     #region IFormattable 
     public override string ToString() 
     { 
      return FValue.ToString(); 
     } 

     public string ToString(IFormatProvider AProvider) 
     { 
      return FValue.ToString(AProvider); 
     } 

     public string ToString(string AFormat) 
     { 
      return FValue.ToString(AFormat, null); 
     } 

     public string ToString(string AFormat, IFormatProvider AProvider) 
     { 
      return FValue.ToString(AFormat, AProvider); 
     } 
     #endregion 
     #endregion 
    } 

답변

4

아니요, C# 언어는 IConvertible 인터페이스에 대해 아무것도 모릅니다. 그것은 Convert.ToType 또는 무엇이든을 부를 경우에만 논다.

당신 전환을 허용 할 경우에/int에서, 당신이 당신의 유형 내에서 명시 적으로 제공해야합니다 :

public static implicit operator int(TCountryID id) 
{ 
    return FValue; 
} 

public static implicit operator TCountryID(int id) 
{ 
    return new TCountryID(id); // You'll need to create this constructor... 
} 

가 개인적으로 열심히 생각하지만이 일을하기 전에 - 암시 적 변환이 적은 코드를 만들 수 있습니다 조심하지 않으면 읽을 수 있습니다. (나는 또한 TCountryID를 호출하는 당신에게을 을하지 좋을 걸 -. T 접두사 .NET 명명 규칙을 따르지 않는 필드 F의 접두사를 사용하여이 IMO, 꽤 이상한입니다.)

+0

감사합니다 존, 그 작동 . 코딩 표준에 관해서는 우리 모두가 다음과 같이 자신을 가지고 있습니다 :-) – TheEdge

+1

@ TheEdge : 글쎄, 독자 분은 가지고 계실지 모르지만 Microsoft는 거의 모든 사람이 따르는 것을 게시합니다. http://msdn.microsoft.com/en-us/library/ms229045.aspx –

1

는 "공용 언어 런타임은 일반적으로 변환 클래스를 통해 IConvertible 인터페이스를 공개 공용 언어 런타임도 IConvertible 인터페이스를 사용합니다. 내부적으로 명시 적 인터페이스 구현에서 Convert 클래스 및 기본 공용 언어 런타임 유형의 변환을 지원하는 데 사용되는 코드를 단순화합니다.

그래도 변환을 호출해야합니다. 예 :

int iTest = 0; 
TCountryID tcidTest; 
iTest = Convert.ToInt32(tcidTest); 
관련 문제