更新於 2024/07/08閱讀時間約 3 分鐘

The Nature of Code閱讀心得與Python實作:1.6 Normalizing Vectors

向量的正規化,是指在不改變向量方向的情況下,讓它的長度變成1,也就是變成單位向量(unit vector)。

要找出向量u的單位向量,記做,其實挺簡單的,計算方式為

= u / ‖u‖ 

稍微計算一下,就可以知道‖‖=1。

在pygame中,可以使用normalize()來做向量的正規化。

在做向量的正規化時,由於要除以向量的長度,所以長度為0的向量,也就是零向量,是沒辦法正規化的。因此,在寫程式的時候,必須先排除零向量的情況,然後才能進行向量正規化。例如,要做向量vec的正規化時,可以這樣寫:

unit_vec = vec.normalize() if vec.length() > 0 else 0*vec

這樣子,如果vec是零向量,就不會進行正規化,而直接把單位向量設定成零向量。要注意的是,視vec是二維或三維向量而定,程式中的0*vec也可以寫成pygame.Vector2(0, 0)pygame.Vector3(0, 0, 0)。寫成0*vec的好處,在於可以不需要多費心去注意vec是二維或三維向量,最後得到的,一定會是和vec有相同維度的零向量。

接下來的這個例子,是由畫面中心點,沿著滑鼠游標位置的方向,畫出長度為50的向量。不管滑鼠游標如何移動改變位置,向量的長度都固定為50。

Example 1.6: Normalizing a Vector

# python version 3.10.9
import sys

import pygame # version 2.3.0


pygame.init()

pygame.display.set_caption("Example 1.6: Normalizing a Vector")

BLACK = (0, 0, 0)
GRAY = (180, 180, 180)
WHITE = (255, 255, 255)

screen_size = WIDTH, HEIGHT = 640, 360
screen = pygame.display.set_mode(screen_size)

FPS = 60
frame_rate = pygame.time.Clock()

center = pygame.Vector2(WIDTH//2, HEIGHT//2)

while True:
for event in pygame.event.get():
if event.type == pygame.QUIT:
pygame.quit()
sys.exit()

screen.fill(WHITE)

mouse = pygame.Vector2(pygame.mouse.get_pos())

pygame.draw.line(screen, GRAY, center, mouse, 3)

# 計算向量及其單位向量,如果向量是零向量,則不進行正規化,並將單位向量設為零向量
vec = mouse - center
unit_vec = vec.normalize() if vec.length() > 0 else 0*vec

# 畫長度為50的向量
endpoint = center + 50*unit_vec
pygame.draw.line(screen, BLACK, center, endpoint, 10)

pygame.display.update()
frame_rate.tick(FPS)


分享至
成為作者繼續創作的動力吧!
© 2024 vocus All rights reserved.