2013-02-07 29 views
7

2つの命令または関数を1秒間にN回実行しようとしています。 これはどのようにJavaで行うことができますか? ..私は手動でピクセルを描画しようとしていないと私は第二の効果当たりの回転の何をしたい...ので、基本的に、それはNを実行する必要があります...ループを1秒でn回実行する方法

//in one second 
while(N) 
{ 
    printf("........."); 
    int x=0; 
    printf("The value of x is "); 
} 

に従いますが、問題は実際には少し深くなったよう第二のための時間(しかし、これは無限に実行されます)事前に

おかげ

+0

これは、あなたがあなたが定期的にOSの者について話している場合、サイクルは1分であなたのループ内で実行されます正確にどのように多くの時間を確認することはできません各繰り返し –

+0

で現在の時刻をチェックビジーループを使用することができますちょうど宿題がある場合。 RTOSが必要か、各サイクル間の時間を測定することで推測してください。 –

+1

1秒間にNのすべての量を実行したい、または正確に1秒間にできるだけ多くのNを実行したいですか? – Adrian

答えて

5

あなたはそれが毎秒正確にN回起こるか確認することはできませんが、それはこのように書きます:

long taskTime = 0; 
long sleepTime = 1000/N; 
while (true) { 
    taskTime = System.currentTimeMillis(); 
    //do something 
    taskTime = System.currentTimeMillis()-taskTime; 
    if (sleepTime-taskTime > 0) { 
    Thread.sleep(sleepTime-taskTime); 
    } 
} 
+0

問題は、それらの指示が1ティックで実行できないということです... 1000/N –

+0

のためにスリープ状態にすることができます。これは問題ではありません - タスク時間を測定し、スリープ時間から引きます。私は答えを編集します... – Dariusz

+0

Nit:これは約N(例えば30以下)の場合にのみ機能します。より大きいNの場合は、睡眠の前に毎回*複数のNを行う必要があります。 –

0

ループをwhile(true)に変更します。

whileループが発生するまでの時間をミリ秒単位で確認してください。 whileループの最後に、ミリ秒で時間を取得し、そのうちの1000が経過したかどうかを確認します。もしそうならbreak

+0

これは助けます...しかし、質問は実際に少し深くなる.. 私は手動でピクセルをプロットしようとしています。それは1秒間にN回実行する必要があります(しかしこれは無限に行われます)。 –

+0

これは...ループが何回繰り返されても1秒間実行されます。それがポイントではありませんでしたか? – Dariusz

+0

私はその質問を誤解しました。私が理解していることは、ループが特定の秒で正確にN回実行されるようにすることです。 –

0

擬似コード:

Create Timer t; 
t.Start; 
int counter = N; 
While ((t.Elapsedtime < 1 Second) AND (N > 0)) 
{ 
    call your_function(); 
    N--; 
} 

your_function() 
{ 
    printf("........."); 
    int x=0; 
    printf("The value of x is "); 
} 
0
long start = System.currentTimeMillis(); 
while (System.currentTimeMillis() - start <= 1000) { 
    // Your code goes here 
} 

それが世話をするのはあなたのコードが1000ミリ秒を超えるループされるということです。実行回数は不確実で、実行ごとに異なる場合があります。

3

私は問題を反転します。ループをN秒に制限しないでください。代わりに、N個の作業単位を所望の時間にわたって均等に処理する。

開始する要因/前回(仕事の率にそのを補間、開始(または前作)から経過した時間を計算し、は、その多くの作業を行う、あります時間と完了した作業の量)。これは、多くのゲーム/アニメーションエンジンの基本的な基盤である"delta time"です。

各ループの最後に「yield」と呼んでください。「いいですね」というか、むしろ99%以上のCPU使用量を食べないようにしてください!歩留り自体には最小の分解能がありますが、効果は一般に適切ですが、特に補間が適切な場合は特に適しています。

補間アプローチが使用されているので、これはそれがより多くのN個の各ループをやって意味場合でも、すべてのN(が割り当てられた時間内実行ができること)のために働く必要があります。また、小さなNに対して特定のループを実行する作業がない可能性もありますが、yieldは、このような「余分なビジーループ」をCPU使用率の点で安価にします。ここ


ここnow戻り小数秒、秒で20「X」Sをプリントアウトするためにいくつかの擬似コードである:開始のオフ補間することは容易である。この場合

rate = 20  // per second - "N times per second" 
done = 0 
goal = 1 * rate // same as rate for 1 second 
start = now() 
while done < goal: 
    target = floor((now() - start) * rate) 
    work = (target - done) // work might be 0, that's okay 
    for 0 upto work: 
     print("x") 
    done += work 
    yield() 

定率式のために時間がかかる。最後の作業(またはループ)からの時間に基づく「デルタ時間」の使用は似ており、離散式がない場合に適していますが、やや複雑で微妙なドリフト誤差につながります。


実際sleep/yieldの時間分解能は実装依存であり、システムによってによって変化します。例えば、それは1ms on Linux to 10-15ms on windowsのような低い値の範囲にあるかもしれません。時間デルタを扱うから加え

sleep期間はダリウスWawerの答えに従って、変更することができます。しかし、これにより複雑さが増し、単純なyieldで十分です。

1

提案されている解決策では魅力的ではありません。反復間のギャップを計算する代わりに、次の反復を実行する絶対時間を計算します。反復は以前のものに依存しないため、これはより正確です。

long startTime = System.currentTimeMillis(); 
long msPerIteration = 1000000/iterationsPerSecond; 
long i=0; 
while (true) { 
    // do stuff 

    long msWaiting = startTime + (msPerIteration * ++i) - System.currentTimeMillis(); 

    if (msWaiting > 0) 
     Thread.sleep(msWaiting); 
} 
関連する問題