객체를 int로 캐스팅하는 더 좋은 방법


179

이것은 아마도 사소한 일이지만 더 좋은 방법은 생각할 수 없습니다. C #에서 객체가되는 변형을 반환하는 COM 객체가 있습니다. 내가 이것을 int로 가져올 수있는 유일한 방법은

int test = int.Parse(string.Format("{0}", myobject))

더 깔끔한 방법이 있습니까? 감사

답변:


362

몇 가지 옵션이 있습니다.

  • (int)— 캐스트 연산자. 개체가 이미 상속 계층 구조의 특정 수준에서 정수이거나 암시 적 변환이 정의 된 경우 작동합니다.

  • int.Parse()/int.TryParse() — 알 수없는 형식의 문자열에서 변환합니다.

  • int.ParseExact()/int.TryParseExact() — 특정 형식의 문자열에서 변환

  • Convert.ToInt32() — 알 수없는 유형의 객체를 변환합니다. 명시 적 및 암시 적 변환 또는 IConvertible 구현이 정의 된 경우이를 사용합니다.

  • as int?— "?"에 유의하십시오. as연산자는 참조 형식에 대해서만, 그리고 내가 사용 그래서 "?" 를 의미합니다 Nullable<int>. " as"연산자는 다음과 같이 작동 Convert.To____()하지만 TryParse()오히려 생각 합니다. 변환이 실패하면 예외를 던지기보다는 Parse()반환 null합니다.

이 중 (int)객체가 실제로 박스형 정수인지 선호 합니다. 그렇지 않으면 Convert.ToInt32()이 경우에 사용 하십시오.

이것은 매우 일반적인 답변입니다. Darren Clark의 답변에 약간의주의를 기울이고 싶습니다. 왜냐하면 여기 에서 구체적인 내용을 다루는 것이 좋지만 늦게 와서 아직 투표하지 않았기 때문입니다. 그는 어쨌든 "inted answer"에 대한 내 투표를 얻습니다. 권장 (int), 실패하면 (int)(short)대신 작동 할 수 있음을 지적하고 실제 런타임 유형을 찾기 위해 디버거를 확인하도록 권장합니다.


나는 실제로 오류가 아니라 요점을 너무 단순화하여 누군가가 그렇게 생각할 수있는 요점을 찾았습니다. 나는 그 문장을 제거하고 권위있는 문서에 대한 링크를 추가했습니다.
Joel Coehoorn

직접 전송이 암시 적 변환과 함께 작동합니까? 나는 그것이 다른 전환이 아닌 박스를 엄격히 해제 할 것이라는 인상을 받았다.
Darren Clark

정확한 답변은 아니지만 다음을 읽으십시오. blogs.msdn.com/ericlippert/archive/2009/03/19/…
Joel Coehoorn

결론은 그것이 단지 박스를 개봉하는 것 이상을 확실히한다는 것입니다. 그렇지 않으면 왜 예를 들어 double을 int로 캐스팅 할 수 있습니까?
Joel Coehoorn

그리고 다른 것들을 읽으면 내 묵시적 ​​/ 명시 적으로 거꾸로 할 수 있지만 어느 쪽이든 그것이 요점을 얻는다고 생각합니다.
Joel Coehoorn

41

캐스트 (int) myobject 작동 해야 합니다.

이것이 잘못된 캐스트 예외를 제공하면 변형 유형이 VT_I4가 아니기 때문일 수 있습니다. 내 생각에 VT_I4가있는 변형은 boxed int로, VT_I2는 boxed short로 변환됩니다.

상자 값 유형에 캐스트를 수행 할 때 상자 유형에 캐스트하는 것만 유효합니다. 예를 들어, 반환 된 변형이 실제로 VT_I2이면 (int) (short) myObject작동합니다.

가장 쉽게 찾을 수있는 방법은 반환 된 객체를 검사하고 디버거에서 해당 유형을 살펴 보는 것입니다. 또한 interop 어셈블리에 반환 값이 표시되어 있는지 확인하십시오MarshalAs(UnmanagedType.Struct)


32

Convert.ToInt32 (myobject);

이것은 myobject가 null 인 경우를 처리하고 예외를 throw하는 대신 0을 반환합니다.


이렇게하면 "ToInt"기호를 확인할 수 없습니다 "라는 메시지가 나타납니다. 예를 들어 내가 사용하는 경우에만 작동합니다 ToInt32.
Tobias Feil

이 방법을 어디에서 찾을 수 있습니까? .Net Framework 라이브러리에 있습니까?
Amir Pourmand امیر پورمند

8

다음 Int32.TryParse과 같이 사용하십시오 .

  int test;
  bool result = Int32.TryParse(value, out test);
  if (result)
  {
     Console.WriteLine("Sucess");         
  }
  else
  {
     if (value == null) value = ""; 
     Console.WriteLine("Failure");
  }

실제로 Parse는 TryParse를 호출하고 TryParse가 false를 반환하면 예외를 발생시킵니다. 따라서 TryParse는 예외가 발생하지 않으므로 예외를 처리하지 않습니다.
사무엘

기술적으로는 둘 다 동일한 메소드 NumberToInt32를 호출하지만 작동하지 않으면 Parse 만 예외를 발생시킵니다.
사무엘

TryParse는 여전히 변형을 문자열로 변환해야합니다. AFAIK 문제는 문자열에서 int로 변환하는 것이 아니라 int 인 변형에서 실제 int로 변환하는 것입니다.
Darren Clark

3

각 캐스팅 방법의 차이점을 나열하고 있습니다. 특정 유형의 주조 핸들이 있지만 그렇지 않습니다.

    // object to int
    // does not handle null
    // does not handle NAN ("102art54")
    // convert value to integar
    int intObj = (int)obj;

    // handles only null or number
    int? nullableIntObj = (int?)obj; // null
    Nullable<int> nullableIntObj1 = (Nullable<int>)obj; // null

   // best way for casting from object to nullable int
   // handles null 
   // handles other datatypes gives null("sadfsdf") // result null
    int? nullableIntObj2 = obj as int?; 

    // string to int 
    // does not handle null( throws exception)
    // does not string NAN ("102art54") (throws exception)
    // converts string to int ("26236")
    // accepts string value
    int iVal3 = int.Parse("10120"); // throws exception value cannot be null;

    // handles null converts null to 0
    // does not handle NAN ("102art54") (throws exception)
    // converts obj to int ("26236")
    int val4 = Convert.ToInt32("10120"); 

    // handle null converts null to 0
    // handle NAN ("101art54") converts null to 0
    // convert string to int ("26236")
    int number;

    bool result = int.TryParse(value, out number);

    if (result)
    {
        // converted value
    }
    else
    {
        // number o/p = 0
    }


2
var intTried = Convert.ChangeType(myObject, typeof(int)) as int?;

1
이 답변이 실제로 유용하다는 것을 알았습니다. 상자 바이트를 int로 캐스팅하고을 사용하여 작동하도록했습니다 Convert.ChangeType. OP에 대한 완벽한 답변이 아닐 수도 있지만 일부에게는 분명히 도움이됩니다!
Philippe Paré

1

도 있습니다 TryParse는 .

MSDN에서 :

private static void TryToParse(string value)
   {
      int number;
      bool result = Int32.TryParse(value, out number);
      if (result)
      {
         Console.WriteLine("Converted '{0}' to {1}.", value, number);         
      }
      else
      {
         if (value == null) value = ""; 
         Console.WriteLine("Attempted conversion of '{0}' failed.", value);
      }
   }

1

이상하지만 허용 된 답변은 캐스트 및 변환에 대해 잘못 보입니다. 내 테스트에서 문서를 읽는 것도 암시 적 또는 명시 적 연산자를 고려해서는 안된다는 의미입니다.

따라서 object 유형의 변수가 있고 "boxed"클래스에 암시 적 연산자가 정의되어 있으면 작동하지 않습니다.

대신 또 다른 간단한 방법이지만 실제로 성능 비용은 동적으로 캐스팅하는 것입니다.

(int) (동적) myObject.

VS의 대화 창에서 시도해 볼 수 있습니다.

public class Test
{
  public static implicit operator int(Test v)
  {
    return 12;
  }
}

(int)(object)new Test() //this will fail
Convert.ToInt32((object)new Test()) //this will fail
(int)(dynamic)(object)new Test() //this will pass

1
이것이 사실 ,하지만 확실히 당신은 당신이 그것을 많이하고있는 경우 프로파일 싶어 뭔가 - dynamic무료 거리가 멀다
마크 Gravell

@MarcGravell 나는 또한 답변에 쓰여진 것처럼 당신에게 전적으로 동의합니다.
eTomm

0
int i = myObject.myField.CastTo<int>();
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.