私が構築している流testingなテストフレームワークで使用される数値型の拡張メソッドを作成しようとしています。基本的に、私はこれをやりたい:
public static ShouldBeGreaterThan<T>(this T actual, T expected, string message)
where T : int || T: double || etc...
where T : struct
は、string
およびbool
にも一致するため、そうではありません。数値型のみを一致させるためにできることはありますか? (具体的には>
および<
演算子を実装する型なので、それらを比較できます...これが日付を一致させることを意味する場合、それは本当に重要ではありません-拡張機能はまだ実行します私が期待するもの。)
この場合、ジェネリックをIComparable
インターフェイスに制限します。これにより、CompareTo
メソッドにアクセスできます。これは、このインターフェイスでShouldBeGreaterThan
の質問に答えることができるためです。
数値型はそのインターフェイスを実装しますが、文字列でも機能するという事実はそれほど気にするべきではありません。
where T : struct,
IComparable,
IComparable<T>,
IConvertible,
IEquatable<T>,
IFormattable
これは数値制約に最も近いものです。すべての数値型はこれら5つのインターフェイスを実装しますが、IFormattableはboolによって実装されておらず、文字列は参照型であるため、適用できません。
これらを実装するものが他にもいくつかあります。たとえば、DateTimeです。したがって、実際には必要ではありませんが、必要のない多くのインスタンス化を防ぎます。
public static bool IsGreaterThan<T>(this T actual, T comp) where T : IComparable<T>
{
return actual.CompareTo(comp) > 0;
}
必要に応じて、構造体制約を追加することもできます。
フィルタとして使用するINumeric
のような一般的なものはないため、数値だけに制限するのは困難です。実際、ここで最も簡単なアプローチは、not制約を主張し、メソッド内でComparer<T>.Default.Compare
を使用することだと思います。
この組み込み型は、ジェネリックIComparable<T>
と非ジェネリックIComparable
の両方をサポートし、Nullable<T>
を介してref-types、value-types、lifted usageをサポートします。
完全なoperatorの使用法については、 MiscUtilのOperator
class およびGreaterThan
などをご覧ください。 really(インターフェースではなく)演算子を使用する場合に便利です。また、Add
などの他の演算子へのアクセスも提供します。
Stackoverflowには、この種の質問が散らばっています。 この検索を見てください 。 C#は、数値で制約されたジェネリック型を定義する方法をサポートしていません。残念ながら、最善の方法は、すべてのオブジェクトに拡張メソッドを実装し、タイプに基づいて切り替えを行うか、int、double、floatなどのメソッドのセットを作成することです。
この回避策が役立つ場合があります: ポリシーを使用した回避策 。コンパイル時の安全性を提供します。