내 프로젝트 중 하나에서 C # 8로 전환했습니다. 그리고 나는 나의 모든 switch진술을 표현 으로 옮겼습니다 . 그러나 나는 내 프로젝트가 다르게 작동하기 시작했고 그것이 switch표현 때문이라는 것을 알았습니다 . 예를 들어이 코드를 얻을 수 있습니다
class Program
{
public enum DataType
{
Single,
Double,
UInt16,
UInt32,
UInt64,
Int16,
Int32,
Int64,
Byte
}
static void Main(string[] args)
{
dynamic value1 = 5;
dynamic value2 = 6;
var casted = CastToType(value1, DataType.Int16);
var casted1 = CastToTypeExpression(value2, DataType.Int16);
var type = casted.GetType(); // Int16
var type1 = casted1.GetType(); // Double
var bytes = BitConverter.GetBytes(casted); // byte arr with 2 el => [5, 0] <- expected behavior
var bytes1 = BitConverter.GetBytes(casted1); // byte arr with 8 el => [0, 0, 0, 0, 0, 0, 24, 64]
}
public static dynamic CastToType(dynamic value, DataType type)
{
switch (type)
{
case DataType.Byte:
return (byte)value;
case DataType.Double:
return (double)value;
case DataType.Int16:
return (short)value;
case DataType.Int32:
return (int)value;
case DataType.Int64:
return (long)value;
case DataType.Single:
return (float)value;
case DataType.UInt16:
return (ushort)value;
case DataType.UInt32:
return (uint)value;
case DataType.UInt64:
return (ulong)value;
default: throw new InvalidCastException();
}
}
public static dynamic CastToTypeExpression(dynamic value, DataType type)
{
return type switch
{
DataType.Byte => (byte)value,
DataType.Double => (double)value,
DataType.Int16 => (short)value,
DataType.Int32 => (int)value,
DataType.Int64 => (long)value,
DataType.Single => (float)value,
DataType.UInt16 => (ushort)value,
DataType.UInt32 => (uint)value,
DataType.UInt64 => (ulong)value,
_ => throw new InvalidCastException(),
};
}
}
결과를 주석으로 작성했지만 클래식 스위치를 사용하면 tl; dr가 값을 캐스팅하면 예상되는 유형의 값이 반환되지만 스위치 식을 사용하면 "더블"의 유형이 반환 byte[]됩니다. 값의 바이트
둘의 차이점은 무엇입니까? 내가 무엇을 그리워합니까?
1
왜 그리고 어떻게 이런 일이 발생하는지 정확하게 설명 할 수는 없지만 여기에서 코드의 디 컴파일 된 버전 ( gist.github.com/MaDOS/4904683d461d022e4b24f4080009ae5e )을 살펴보면 컴파일러가 가능한 모든 반환 유형을 알 수 있음을 알 수 있습니다 의 표현식은 double에 맞고 결과가 반환 될 때마다 저장할 double을 자동으로 선언합니다. ( gist.github.com/MaDOS/… )
—
Robin B