2014-10-24 9 views
6

기존 코드에서 유니버설 클래스 라이브러리를 만들고 있는데, 그 컴파일러의 수명을 위해 컴파일러 경고를 받는다.어떻게 Marshal.SizeOf (Object)를 Marshal.SizeOf로 바꿀 수 있습니까? <T>()?

나는 다음과 같은 코드가 있습니다

코드 빌드,하지만

void SomeMethod(Object data) 
{ 
    var size = Marshal.SizeOf(data); 
    ... 
} 
유니버설 프로젝트 (그리고, 내 생각, .NET 4.5.1 이상 프로젝트) 나는 다음과 같은 컴파일러 경고를 받게에서 :

경고 CS0618 : 'System.Runtime.InteropServices.Marshal.SizeOf (object)'가 사용되지 않음 : 'SizeOf (개체)가 향후 릴리스에서 사용하지 못할 수 있습니다. 대신 SizeOf <T>()을 사용하십시오.

위의 경우 일반 매개 변수가없는 방법 Marshal.SizeOf<T>()을 사용하여 Marshal.SizeOf(Object)의 대체품을 어떻게 만듭니 까? 이론적으로 어떤 유형이 data인지 전혀 알지 못합니다.

Marshal.SizeOf(Object)을 사용하는 것은 그것이 Obsolete으로 간주 되었기 때문에 나쁜 관행으로 간주됩니까? 그리고 take-home 메시지는 실제로 "코드를 완전히 리팩터링"해야합니다.

+3

확실히 4.5.1에서 사용되지 없습니다. .NET 네이티브 사전 컴파일러의 목에 통증이 있기 때문에 범용 참조 어셈블리에서 특히 쓸모 없게되었습니다. SomeMethod를 일반적인 것으로 만들 수없는 이유는 분명하지 않습니다. 그렇게 할 수 없다면 .NET 네이티브 툴체인도 문제가 발생할 것입니다. –

+1

답변을 삭제했습니다. [SizeOf (T) on MSDN] (http://msdn.microsoft.com/en-us/library/vstudio/dn261467(v=vs.110) .aspx)을 참조하십시오. 그것은''과 매개 변수를 취합니다. 거기에 물건을 건네면 제대로 측정됩니다. Marhal.SizeOf (데이터)를 성공적으로 전달할 수 있어야합니다. 이것을 가리키는 네마냐 보릭에게 영광. 나는 그것이 실제로 작동한다면 나는 (4.5.1 컴파일러를 가지고 있지 않다는 것을) 확인할 수 없기 때문에 그 대답을 쓰지는 않는다. 그러나 나는 왜 그것이 최종 객체를 가져야 하는지를 보지 못한다. 그리고 그것을 읽을 수있다. 진짜 유형. – quetzalcoatl

+0

귀하의 모든 도움에 감사드립니다, @quetzalcoatl 및 NemanjaBoric. 나는 그 'SizeOf' 과부하를 놓치기를 바보처럼 느낍니다. 나는 그것을 시험해보고 그것이 나의 필요에 얼마나 잘 맞는지 보게 될 것이다. –

답변

0

좋아, 귀하의 의견을받은 후 당신이 필요로하는 모든이 이미있는 것 같습니다 :

SizeOf<T>(T) :이 당신이 필요로하는 방법입니다 생각하지만, 당신은 명시 적으로 일반 매개 변수를 정의 할 필요가 없습니다 인해 ~ type inference. 당신은 간단하게 var size = Marshal.SizeOf(myStructure);을 쓰고 컴파일러는 주어진 객체에서 유형을 추출하고 generic 매개 변수를 채 웁니다.

SizeOf<T>() : 이 방법은 자신의 클래스가 이미 제너릭 클래스이고 어쩌면 T이지만 사용 된 제네릭 유형의 실제 인스턴스가없는 경우에 유용합니다. 이 경우이 방법을 선택해야합니다. 어떻게 반사 방식에 대한

는 :

private static int MySizeOf(object structure) 
{ 
    var marshalType = typeof(Marshal); 
    var genericSizeOfMethod = marshalType.GetMethod("SizeOf", Type.EmptyTypes); 
    var sizeOfMethod = genericSizeOfMethod.MakeGenericMethod(structure.GetType()); 
    var size = (int)sizeOfMethod.Invoke(null, null); 

    return size; 
} 

+1

흥미로운 생각이지만, 나는이 문제를 해결하기 위해 리플렉션에 의존하는 방법을 도입하는 것에 완전히 만족하지는 않습니다. 나는 또한 당신의 코드가 약간의 적응을 필요로한다고 생각한다 : (1)'Type.GetMethod'가 유니버설 프로젝트에서 사용 가능하지 않다고 생각하면'SizeOf' 오버로드를 얻기 위해'TypeInfo.DeclaredMethods'를 트래버스해야한다. (2)'structure' 객체를 메서드에 전달할 기회가 없다고 생각합니다. 아마도 Invoke 호출의 두 번째 인수는 null 대신 new [] {structure}가되어야할까요? –

+0

유니버설과 함께 일한 적이 없으므로 제한을 알지 못합니다. Invoke 호출의 경우 구조체를 전달할 필요가 없습니다. 이미 형식을 추출하여 Marshal.SizeOf ()'일반 호출에 사용했습니다. – Oliver

+0

그러나'structure' 객체의 관리되지 않는 크기는 항상 같은 것입니까? 그럼 왜 [Marshal.SizeOf '과 [Marshal.SizeOf ()'및 [Marshal.SizeOf (T)]가 [4.5.1 이후 프레임 워크] (http : // msdn. microsoft.com/en-us/library/vstudio/system.runtime.interopservices.marshal.sizeof(v=vs.110).aspx)? 그리고 유니버설 프로젝트에서'Type.GetMethod'를 할 수 없다는 것이 확실합니다. 왜냐하면이 방법은 최신 Windows (f.k.a. Metro) 응용 프로그램에서는 사용할 수 없기 때문입니다. –