3

私は単純なレーサーアプリを作成するために xaml に従っています

<StackPanel>
    <Slider x:Name="racerOne" Maximum="1000"/>
    <Slider x:Name="racerTwo" Maximum="1000"/>
    <Button Content="Start Race" Click="myButton_Click"/>
</StackPanel>

次のコードを使用します

    private void myButton_Click(object sender, RoutedEventArgs e)
    {
        Task firstRacer = Task.Run(() => Race(racerOne));
        Task secondRacer = Task.Run(() => Race(racerTwo));
    }

    private void Race(Slider racer)
    { 
        int step = 0;

        while (step < 1000)
        {
            step += new Random().Next(0, 10);
            Dispatcher.BeginInvoke(new ThreadStart(() => racer.Value = step));
            Thread.Sleep(new Random().Next(0, 300));
        }
    }

ほとんどの場合 (90% としましょう)、両方のスライダーが一緒に動いているように見えますが、デバッグでは、各スレッドが に対して異なる値を生成することがわかりますstep。どうして?

4

3 に答える 3

5

Randomクロックによってシードされます。あなたは次のようなことをしたいかもしれません:

Random rand1 = new Random();
Random rand2 = new Random(rand1.Next());
Task firstRacer = Task.Run(() => Race(racerOne, rand1));
Task secondRacer = Task.Run(() => Race(racerTwo, rand2));

private void Race(Slider racer, Random rand)
{ 
    int step = 0;

    while (step < 1000)
    {
        step += rand.Next(0, 10);
        Dispatcher.BeginInvoke(new ThreadStart(() => racer.Value = step));
        Thread.Sleep(rand.Next(0, 300));
    }
}

これにより、異なるシードを持つRandom2 つの個別のインスタンスが作成され (1 番目を使用して 2 番目をシードすることにより)、これらをas 引数に渡します。これにより、タイミングが原因で過度に予測可能な動作が発生するリスクがなくなります。Race

于 2013-11-14T09:59:25.657 に答える