35

安全な方法はありますか?最小限のケース ステートメントでアングル ラップを処理するだけです。

角度の特定の表現 (0 ~ 360 度または -180 ~ 180 度 (または同等のラジアン)) を使用し、角度をラップすると、角度ラップが発生します。たとえば、角度が -170 で、50 度を引くとします。数学的には -220 まで足しますが、実際には +140 度になるはずです。

明らかに、次を使用してこれを確認できます。

if (deg < -180) { 180 - abs(deg + 180); }

または類似。しかし、第一に、多数のチェックが必要であり、第二に、2 回ラップすると機能しません。

これが一般的な 2 番目のケースは、2 つの角度間の補間です。

たとえば、-170 度と 160 度の角度があり、それらの中間が必要だとします。これを行う一般的な方法は次のとおりですang1 + 0.5(ang2-ang1)が、私が提供した例では、角度が 175 になるはずの角度が -5 度になります。

これらのシナリオでアングル ラップを処理する一般的な方法はありますか?

4

6 に答える 6

68

完全を期すために、正規化[0, 360)[-180, 180)正規化の両方を含めます。

が必要になります#include <math.h>


正規化[0,360):

double constrainAngle(double x){
    x = fmod(x,360);
    if (x < 0)
        x += 360;
    return x;
}

正規化[-180,180):

double constrainAngle(double x){
    x = fmod(x + 180,360);
    if (x < 0)
        x += 360;
    return x - 180;
}

パターンは、ラジアンに一般化できるほど簡単に認識できる必要があります。


角二等分:

double angleDiff(double a,double b){
    double dif = fmod(b - a + 180,360);
    if (dif < 0)
        dif += 360;
    return dif - 180;
}
double bisectAngle(double a,double b){
    return constrainAngle(a + angleDiff(a,b) * 0.5);
}

これは、「小さい」側の角度を二等分する必要があります。(警告: 完全にはテストされていません)

于 2012-07-16T04:48:03.620 に答える
20

remainder()数学ライブラリからの使用は便利だと思います。angleaを指定して、それを -180, 180 に制限するには、次のようにします。

remainder(a, 360.0);

をラジアンに変更し360.0ます2.0 * M_PI

于 2012-07-16T11:44:54.847 に答える
5

したがって、Angle を制約する Mystical のアプローチを使用して、私が望むことを効果的に行う方法を見つけた場合。ここにあります:

ここに画像の説明を入力

これは、私が考えることができるすべての例で機能するようです。

于 2012-07-17T00:14:44.240 に答える
-1

angle(+PI ~ -PI) を signed int 値 (または short 値) にマップします。

angle_signed_short = angle_float / PI * 0x7FFFF;

その後、通常どおり値を追加または削除できます。次に、マップを戻します。

angle_float = angle_signed_short * PI / 0x7FFFF;
于 2015-11-24T09:06:09.620 に答える