[解決済み】2つのベクトル間の時計回りの角度を直接計算する方法
質問
2つのベクトル(2D, 3D)の間の時計回りの角度を求めたい。
内角(0-180度)を求めるには、ドットプロダクトを使うのが一般的ですが、結果が必要な角度かその補数かを判断するには、いくつかの if ステートメントを使う必要があります。
時計回りの角度を直接計算する方法をご存じですか?
どのように解決するのですか?
2Dケース
と同じように ドットプロダクト は角度の余弦に比例するので 行列式 はその正弦に比例する。ですから、このように角度を計算することができます。
dot = x1*x2 + y1*y2 # dot product between [x1, y1] and [x2, y2]
det = x1*y2 - y1*x2 # determinant
angle = atan2(det, dot) # atan2(y, x) or atan2(sin, cos)
この角度の向きは、座標系の向きと一致する。において 左利き座標系 すなわち x 右向きで y コンピュータグラフィックスで一般的なように、時計回りの角度を正の符号で表すことになる。座標系の向きが数学的に y を上にすると、数学の慣習に従って反時計回りの角度になります。入力の順番を変えると符号が変わるので、符号に不満がある場合は入力を入れ替えればよい。
3Dの場合
3Dでは、任意に配置された2つのベクトルが、両者に垂直な独自の回転軸を定義します。その回転軸の向きは固定されていないので、回転角の向きも一意には決められないことになります。よくある慣習として、角度を常に正とし、正の角度に合うような軸の向きにすることがある。この場合、角度の計算は正規化されたベクトルの内積で十分である。
dot = x1*x2 + y1*y2 + z1*z2 #between [x1, y1, z1] and [x2, y2, z2]
lenSq1 = x1*x1 + y1*y1 + z1*z1
lenSq2 = x2*x2 + y2*y2 + z2*z2
angle = acos(dot/sqrt(lenSq1 * lenSq2))
3Dに埋め込まれた平面
特殊なケースとして、ベクトルが任意に配置されるのではなく、既知の法線ベクトルを持つ平面内に存在する場合があります。 n . このとき、回転軸の方向は n の方向も同じであり n は、その軸の向きを固定します。この場合、上記の2次元の計算を適応させることができ、その中には n を 行列式 を使い、3×3の大きさにします。
dot = x1*x2 + y1*y2 + z1*z2
det = x1*y2*zn + x2*yn*z1 + xn*y1*z2 - z1*y2*xn - z2*yn*x1 - zn*y1*x2
angle = atan2(det, dot)
これが機能するための一つの条件は、法線ベクトルが n は単位長さを持っています。そうでない場合は、正規化する必要があります。
トリプルプロダクトとして
この行列式は、次のように表すこともできる。 三重積 というように エクスキューブレン が編集案で指摘されました。
det = n · (v1 × v2)
これは、ある種のAPIでは実装しやすいかもしれませんし、ここで起こっていることを別の観点から見ることができます。角度の正弦に比例し、平面に対して垂直になるため、積は n . したがって、内積は基本的にそのベクトルの長さを測りますが、正しい符号が付加されたものになります。
関連
-
[解決済み】C++のGetlineの問題(オーバーロードされた関数 "getline "のインスタンスがない
-
[解決済み] error: 'if' の前に unqualified-id を期待した。
-
[解決済み] 非常に基本的なC++プログラムの問題 - バイナリ式への無効なオペランド
-
[解決済み】オブジェクト引数のない非静的メンバ関数の呼び出し コンパイラーエラー
-
[解決済み】C++の余分な資格エラー
-
[解決済み】クラステンプレートの使用にはテンプレート引数リストが必要です
-
[解決済み] [Solved] インクルードファイルが開けません。'stdio.h' - Visual Studio Community 2017 - C++ Error
-
[解決済み] to_string は std のメンバーではない、と g++ が言っている (mingw)
-
[解決済み] 整数の平方根が整数であるかどうかを判断する最速の方法
-
[解決済み] Intel CPU の _mm_popcnt_u64 で、32 ビットのループカウンターを 64 ビットに置き換えると、パフォーマンスが著しく低下します。
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
[解決済み】C++コンパイルタイムエラー:数値定数の前に期待される識別子
-
[解決済み】致命的なエラー LNK1169: ゲームプログラミングで1つ以上の多重定義されたシンボルが発見された
-
[解決済み】C++の変数はイニシャライザーを持っているが、不完全な型?
-
[解決済み】c++でstd::vectorを返すための効率的な方法
-
[解決済み】Visual C++で "Debug Assertion failed "の原因となる行を見つける。
-
[解決済み] 式はクラス型を持つ必要があります。
-
[解決済み】C++の余分な資格エラー
-
[解決済み] 数値定数の前にunqualified-idを付けて、数値を定義することを期待する。
-
[解決済み】警告 - 符号付き整数式と符号なし整数式の比較
-
[解決済み】Eclipse IDEでC++エラー「nullptrはこのスコープで宣言されていません」が発生する件