1

本当に必要System.Lazyですか?クラスライブラリに100個の静的クラスがあり、各静的クラスが平均100個の静的System.Lazys = 10000 System.Lazysを使用しているとしましょう。これは、クラスライブラリを使用するプログラムの起動時に開始する必要がありますか?

つまり、通常は1つのクラスライブラリだけを使用するのではなく、15個の.dllをインポートすると、それぞれに大量の静的System.Lazysが含まれます。これらすべてのSystem.Lazysを開始するには、長い時間がかかると確信しています。言うまでもなく、大量のメモリも蓄積されます(それぞれに独自のSystem.Funcがあるため、メモリ内にそれぞれ50バイト= 500kbに​​配置しましょう)

だから私は疑問に思っていました..それを「古い」方法で行うのが最善ですか(ブール値を使用して何かが開始されたかどうかを追跡するなど)

4

3 に答える 3

7

Lazy1)インスタンスが不要になる可能性が高く、2)インスタンスを起動するコストがオーバーヘッドを正当化するのに十分高い場合にのみ、使用する必要があります。

クラスに100人の静的な怠惰なメンバーがいる場合、ほぼ間違いなく間違っています。

于 2011-04-23T19:03:30.150 に答える
3

他の人が言っているように、この種の怠惰な初期化が必要な場合は、はるかに大きな問題が発生します。

しかしとにかく、この質問を自分でどのように処理する必要があるかを示すためだけに、仮定を立てる前に測定してください。

以下のプログラム(ayendeに触発された)は、単に新しいオブジェクトを割り当てるLazy()インスタンスの作成と初期化のオーバーヘッドを測定します。

私のマシンでの出力:

Created 583599 objects in 00:00:01.0000117
Created 679939 objects in 00:00:01.0039926
Created 688751 objects in 00:00:01.0000013
Created 678244 objects in 00:00:01.0000018
Created 682506 objects in 00:00:01.0000018
Created and initialized 516400 lazy objects in 00:00:01.0000018
Created and initialized 526585 lazy objects in 00:00:01.0000049
Created and initialized 519425 lazy objects in 00:00:01.0000018
Created and initialized 514477 lazy objects in 00:00:01.0000022
Created and initialized 523544 lazy objects in 00:00:01.0005176
Performance loss: 21,5091944284387 %

多くの場合、パフォーマンスの問題は目前の状況に非常に固有であるため、これから一般的な結論を導き出さないでください。

しかし、ご覧のとおり、オブジェクトをインスタンス化するオーバーヘッドは、インスタンス化を遅らせるLazyことが役立つ(つまり、高価で、構築されたオブジェクトがそうでない可能性が高い)状況で通常発生するnewことを考えると、比較的小さいです。Lazy実際に必要)

class Program
{
static void Main(string[] args)
    {
        var sequence = Enumerable.Range(1, 5);

        var q1 = from s in sequence
                 select GenerateSimpleObjects();

        var q2 = from s in sequence
                 select GenerateAndInitializeLazies();

        var m1 = q1.Average();
        var m2 = q2.Average();

        Console.WriteLine("Performance loss: {0} %", 100 - 100 * m2/m1);

    }

    static void GenerateSimpleObjects()
    {
        var sp = Stopwatch.StartNew();

        int i = 0;
        while (sp.ElapsedMilliseconds < 1000)
        {
            new object();
            i++;
        }
        sp.Stop();
        Console.WriteLine("Created {0} objects in {1}", i, sp.Elapsed);
    }


    static void GenerateAndInitializeLazies()
    {
        var sp = Stopwatch.StartNew();

        int i = 0;
        while (sp.ElapsedMilliseconds < 1000)
        {
            var l = new Lazy<object>(() => new object());
            var o = l.Value;
            i++;
        }
        sp.Stop();
        Console.WriteLine("Created and initialized {0} lazy objects in {1}", i, sp.Elapsed);
    }
}
于 2011-04-23T20:00:15.953 に答える
2

Lazy<T>グラフ内のオブジェクトを遅延ロードすることが理にかなっている場合は、慎重に使用することを目的としています。つまり、必要ではない可能性が高いが必要になる可能性があるオブジェクトの場合、およびそれらをフェッチするためのコストが高い場合です。

そのため、彼らは素晴らしい解決策です。

すべてのオブジェクトを使用することがわかっている場合は、を使用しないでくださいLazy<T>

于 2011-04-23T19:04:16.997 に答える