ベクトルの内積
2本の矢印の「向きの近さ」を1つの数値にする
- 1
- 2本のベクトルの「向きの揃い具合」を1つの数値に変換する演算である。
- 2
- 2本のベクトルが垂直(90°)に交わるとき、内積はちょうど 0 になる。
- 3
- ゲーム制作での敵の視界判定(FOV)や、AIのレコメンド(コサイン類似度)の中核技術。
なぜこれを学ぶのか? — 現実社会とテクノロジーでの価値
なぜ生まれたのか?
2つのベクトルが「どれくらい同じ方向を向いているか」を、角度を測らずに掛け算と足し算だけで超高速に計算するために考案された。
身につく武器・思考力
多次元のデータ同士の類似度を一瞬で割り出し、影の長さや仕事量を瞬時に導く線形代数の最重要直感が手に入る。
実社会・ITでの活躍現場
- •ChatGPTやAI検索における文章同士の意味の近さ(コサイン類似度)
- •3Dゲームにおける敵の視野角判定(プレイヤーが視界内にいるか)
- •CGにおけるポリゴンの陰影計算(面と光の角度による明るさ)
- •物理学における力学の「仕事(W = F · s)」の計算
Layer 1 — 直感・シミュレーター
上のシミュレーターで青と赤の矢印の先端をドラッグしてみよう。2本が同じ方向を向くほど内積は大きくなり、直角(90°)でちょうど0になり、反対方向を向くと負になる。まずは数式抜きで、この「向きの近さのメーター」としての感覚をつかもう。
↑ 矢印の先端をドラッグして、2本のベクトルの向きと大きさを自由に変えてみよう。内積の値と、なす角の関係を確認できる。
2つのベクトル a=(1, 0) と b=(0, 1) の内積の値は何になるでしょう?
Layer 2 — 定義・受験・証明
定義
2つのベクトル の内積(ドット積)は、成分計算では次のように定義される。
これは幾何的には、なす角 を使って次のようにも表せる。
この2つの式が一致することが、内積の最も重要な性質である。
公式・数理モデル
証明・導出
余弦定理を使うと成分表示と幾何表示が一致することを示せる。 の始点をそろえたとき、終点間の距離を とすると余弦定理より
一方で成分計算からも が導けるため、両辺を比較すると
が得られ、幾何表示と成分表示が一致することが証明される。
押さえておきたいポイント
- 内積が正 → 2つのベクトルは90°未満(似た方向)を向いている
- 内積が0 → 2つのベクトルは直交している(垂直)
- 内積が負 → 2つのベクトルは90°より開いた方向を向いている
- より、内積からなす角を逆算できる
本トピックの内容・数理モデルは、文部科学省学習指導要領(算数・数学・情報)および国際標準カリキュラムに準拠し、エンジニアリング現場の実装事例と照らし合わせてMath World Lab編集部により検証・作成されています。
Layer 3 — 工学応用・現場実装
ゲーム制作の視野角判定 (FOV: Field of View)
敵キャラクターが「プレイヤーが自分の視野角の中に入っているか」を判定する処理は、内積を使うと数行で書ける。敵の向きベクトルとプレイヤーへの方向ベクトルの内積からなす角の余弦を求め、視野角の半分の余弦と比較するだけでよい。平方根や三角関数を使わずに高速に判定できるのが実務上のポイント。
1type Vec2 = { x: number; y: number };23function normalize(v: Vec2): Vec2 {4 const len = Math.hypot(v.x, v.y) || 1;5 return { x: v.x / len, y: v.y / len };6}78function dot(a: Vec2, b: Vec2): number {9 return a.x * b.x + a.y * b.y;10}1112/**13 * 敵の視野角(fovDegrees, 全体角度)の中にターゲットが入っているか判定する。14 * 平方根や atan2 を避け、cos の比較だけで済ませるのがポイント。15 */16function isInFieldOfView(17 enemyPos: Vec2,18 enemyFacing: Vec2, // 正規化済みの向きベクトル19 targetPos: Vec2,20 fovDegrees: number,21): boolean {22 const toTarget = normalize({23 x: targetPos.x - enemyPos.x,24 y: targetPos.y - enemyPos.y,25 });2627 const cosTheta = dot(enemyFacing, toTarget);28 const cosHalfFov = Math.cos((fovDegrees / 2) * (Math.PI / 180));2930 // cosThetaが大きいほど「正面に近い」。しきい値以上ならFOV内。31 return cosTheta >= cosHalfFov;32}3334// 使用例: 敵は右(1,0)向き、視野角90度35const enemy = { x: 0, y: 0 };36const facing: Vec2 = { x: 1, y: 0 };37const player = { x: 5, y: 3 };3839console.log(isInFieldOfView(enemy, facing, player, 90)); // true / false
次に学ぶならコレ!おすすめトピック
この単元と深い繋がりを持つ、あわせて学ぶと理解が深まるおすすめ単元