C#

配列のindexが範囲外であることをtry-catchで判定してはいけないパフォーマンス上の理由

例外投げる言語でcatchで判定できてもLengthで見てくださいねというだけの話なんですが、
パフォーマンスが想像よりずっとひどかったです。

コード

using System;

namespace PlayGround
{
    class Program
    {
        static void Main(string[] args)
        {
            var c = 100;
            var sw = new System.Diagnostics.Stopwatch();

            var res = 0;
            var arr = new int[] { 0, 1, 2 };

            // try-catch
            sw.Start();
            for (int i = 0; i < c; i++)
            {
                try
                {
                    res = arr[i];
                }
                catch
                {
                    res = 0;
                }
            }
            sw.Stop();
            Console.WriteLine(sw.Elapsed.ToString());

            // if
            sw.Restart();
            for (int i = 0; i < c; i++)
            {
                if (arr.Length > i)
                {
                    res = arr[i];
                }
                else
                {
                    res = 0;
                }
            }
            sw.Stop();
            Console.WriteLine(sw.Elapsed.ToString());
        }
    }
}

出力

00:00:20.4056930
00:00:00.0000030

オオウ。
100回中97回例外投げるだけで20sとは…。変に横着してはいけませんね。

追記

上記がDebugビルドだったのでReleaseビルドで計測。

// c=100
00:00:00.0038820
00:00:00.0000010

// c=1000000
00:00:23.8697330
00:00:00.0007260

100万で20sに。やはり無視できないサイズですね。