なぜCount()メソッドは「checked」キーワードを使用するのですか?


23

CountとCount()の違いを探していたので、のソースコードをちらりと見ようと思いましたCount()。次のコードスニペットを見て、checkedキーワードが必要である、または必要である理由を知りました。

int num = 0;
using (IEnumerator<TSource> enumerator = source.GetEnumerator())
{
    while (enumerator.MoveNext())
    {
        num = checked(num + 1);
    }
    return num;
}

ソースコード:

// System.Linq.Enumerable
using System.Collections;
using System.Collections.Generic;

public static int Count<TSource>(this IEnumerable<TSource> source)
{
    if (source == null)
    {
        ThrowHelper.ThrowArgumentNullException(ExceptionArgument.source);
    }
    ICollection<TSource> collection = source as ICollection<TSource>;
    if (collection != null)
    {
        return collection.Count;
    }
    IIListProvider<TSource> iIListProvider = source as IIListProvider<TSource>;
    if (iIListProvider != null)
    {
        return iIListProvider.GetCount(onlyIfCheap: false);
    }
    ICollection collection2 = source as ICollection;
    if (collection2 != null)
    {
        return collection2.Count;
    }
    int num = 0;
    using (IEnumerator<TSource> enumerator = source.GetEnumerator())
    {
        while (enumerator.MoveNext())
        {
            num = checked(num + 1);
        }
        return num;
    }
}

2
.NET 4.0にはまだこのチェックがありませんでしたが、4.5にはありました。これは、WinRTイテレータの問題を回避するために行われた可能性があります。uintを使用していることに注意してください。
ハンスパッサント

回答:


35

シーケンスに20億を超える奇数のアイテムが存在する(確かにありそうもない)イベントで負の数を返すことを望まないため、または(負の可能性は低い)ケースでは負ではないが誤った数を返すシーケンスには40億以上のアイテムがあることを確認します。checkedオーバーフロー状態を検出します。


1
@DavidMårtenssonC#のデフォルトはunchecked; checkedただし、コンパイラスイッチを介してデフォルトでグローバルレベルに切り替えることができますが、率直に言って、使用されることはめったにないので、C#が「通常」checkedモードで実行されることを示唆するのは非常に間違っていると思います。また、unsafeインタラクションがないことに注意してくださいunchecked
マークグラベル

1
それは私にとってニュースでした、私はこれを書く前にプロジェクトでテストしました、そしてそれをチェックしないで追加するまでC#はオーバーフローについて不平を言いましたか?編集:「定数式(コンパイル時に完全に評価できる式)の場合、デフォルトのコンテキストは常にチェックされます。定数式がチェックされていないコンテキストに明示的に配置されていない限り、コンパイル中に発生するオーバーフロー式の評価時にコンパイルエラーが発生します。」
DavidMårtensson

@DavidMårtenssonああ、はい-良いニュアンス。ランタイムについて話していました。あなたが言うように:コンパイル時間は異なります
マークグラベル

しかし、コンパイル時間は投稿の例には適用されないため、私のコメントは間違っていたので削除しました。
DavidMårtensson
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.