web-dev-qa-db-ja.com

角度を+/-πラジアンに正規化する標準的な方法Java

Javaで、角度を+/-πに正規化するためのライブラリ関数またはよく知られた迅速で効率的な方法はありますか?たとえば、2つの角度を追加する場合などです。

私が今持っているのは( この答え に基づいて)基本的に以下のコードです...

private static final double TWO_PI = 2 * Math.PI;

double normalize(double theta) {
    double normalized = theta % TWO_PI;
    normalized = (normalized + TWO_PI) % TWO_PI;
    return normalized <= Math.PI ? normalized : normalized - TWO_PI;
}

...しかし、少し複雑でパフォーマンスの面では、モジュロ演算子には興奮していません。 (thetaが比較的大きな数ではないことを保証できないことに注意してください。したがって、ループのない純粋な加算/減算ソリューションはないと思います。実際には、手巻きループの方法がわかりません。 %と比較する可能性があります。)

私が使用できる十分にテストされた最適化されたライブラリ関数、またはより良いアルゴリズムはありますか、それともこれはそれが得るのと同じくらい良いですか?

12
David Moles

Apacheコモンズには次のものがあります。

http://commons.Apache.org/proper/commons-math/javadocs/api-3.6.1/org/Apache/commons/math3/util/MathUtils.html#normalizeAngle(double、double) ==

-πと+πの間の角度を正規化します

a = MathUtils.normalizeAngle(a, 0.0);

そして、ソースコードを見ると、これで再現できます(独自のFastMath.floorを使用しますが、外部ライブラリなしで実行したい場合):

theta - TWO_PI * Math.floor((theta + Math.PI) / TWO_PI)

ソースはここにあります: https://github.com/Apache/commons-math/blob/53ec46ba272e23c0c96ada42f26f4e70e96f3115/src/main/Java/org/Apache/commons/math4/util/MathUtils.Java#L107


将来の読者への注意:このメソッドは(2017年6月) 削除されました 最新のコモンズから-数学4。 xコードベース。この後のバージョンを使用している場合は、代わりに commons-numbers を使用することをお勧めします(リリースされた後)-現在:

a = PlaneAngleRadians.normalizeBetweenMinusPiAndPi(a);

または

a = PlaneAngleRadians.normalize(a, 0.0);
16
CupawnTae

100%確実な方法は1つだけです。

public static double normalizeAngle(double angle) {
    return Math.atan2(Math.sin(angle), Math.cos(angle));
}   

他のすべては、賢くなりすぎて失敗しようとしている人々です。

7
cohadar