ジェネリック型を使用し、struct制約があればこんなコードですが、
voidFunc<T>(T?val)whereT:struct{Console.WriteLine(val.Value.GetHashCode());}long?value=long.MaxValue;Func(value);これを制約なしでアクセスしたいわけです。
voidFunc<T>(Tval){Console.WriteLine(val.Value.GetHashCode());^^^^^//アクセスできない}long?value=long.MaxValue;Func(value);実行時にNullable.GetUnderlyingType(typeof(T));でSystem.Typeを取得してリフレクションでも取得できますが、もう少し効率の良さそうな方法を取りたいので、Expression式を使います。
Expression式を使用したサンプルコード
usingSystem;usingstaticSystem.Linq.Expressions.Expression;staticclassInnerValueHashCode{publicstaticintGet<T>(Tvalue)=>Impl<T>.Delegate(value);privatestaticclassImpl<T>{publicstaticFunc<T,int>GenerateFunc(){varnullableValue=Parameter(typeof(T),"nullableValue");varunderlyingType=Nullable.GetUnderlyingType(typeof(T));varcallExpression=Call(Property(nullableValue,typeof(T),"Value"),underlyingType.GetMethod("GetHashCode",Type.EmptyTypes));varlambda=Lambda<Func<T,int>>(callExpression,nullableValue);returnlambda.Compile();}internalreadonlystaticFunc<T,int>Delegate=GenerateFunc();}}long?value=long.MaxValue;InnerValueHashCode.Get(value);もちろん Nullable<T>以外を渡すと正しく動作しないので、事前にジェネリック型のチェックは必要です。