向量的基本运算
2025年2月16日大约 4 分钟
向量的基本运算包括向量的加法、减法、数乘、点积和叉积。这些运算不仅在数学中具有重要意义,还广泛应用于物理、工程和计算机科学等领域。下面分别介绍这些运算及其几何意义。
基本运算
1. 向量的加法
- 运算:设有两个向量
和 ,它们的和 定义为: - 几何意义:向量加法的几何意义是将两个向量首尾相连,结果向量是从第一个向量的起点指向第二个向量的终点的向量。这被称为向量的平行四边形法则。
2. 向量的减法
- 运算:设有两个向量
和 ,它们的差 定义为: - 几何意义:向量减法的几何意义是将两个向量的起点重合,结果向量是从第二个向量的终点指向第一个向量的终点的向量。
3. 向量的数乘
- 运算:设有一个向量
和一个标量 ,它们的数乘 定义为: - 几何意义:向量数乘的几何意义是将向量的长度乘以标量的绝对值,方向保持不变(如果标量为正)或反向(如果标量为负)。
4. 向量的点积
- 运算:设有两个向量
和 ,它们的点积 定义为: - 几何意义:向量点积的几何意义是两个向量的长度和它们之间夹角的余弦值的乘积。如果两个向量垂直,它们的点积为零。用公式表示为:
其中, 是向量 和 之间的夹角。
5. 向量的叉积
- 运算:设有两个向量
和 ,它们的叉积 定义为: - 几何意义:向量叉积的几何意义是生成一个垂直于两个向量所在平面的向量,其长度等于两个向量形成的平行四边形的面积,方向由右手定则确定。用公式表示为:
其中, 是向量 和 之间的夹角。
这些基本运算不仅在数学中具有重要意义,还广泛应用于物理、工程和计算机科学等领域。
C#代码实现
public class Point3D
{
public double X { get; set; }
public double Y { get; set; }
public double Z { get; set; }
public Point3D()
{
}
public Point3D(double x, double y, double z)
{
this.X = x;
this.Y = y;
this.Z = z;
}
public static Point3D operator +(Point3D a, Point3D b)
{
return new Point3D(a.X + b.X, a.Y + b.Y, a.Z + b.Z);
}
public static Point3D operator -(Point3D a, Point3D b)
{
return new Point3D(a.X - b.X, a.Y - b.Y, a.Z - b.Z);
}
/// <summary>
/// 标量乘法
/// </summary>
/// <param name="scalar"></param>
/// <param name="b"></param>
/// <returns></returns>
public static Point3D operator *(double scalar, Point3D b)
{
return new Point3D(scalar * b.X, scalar * b.Y, scalar * b.Z);
}
public static Point3D operator *(Point3D b, double scalar)
{
return scalar * b;
}
/// <summary>
/// 点积
/// </summary>
/// <param name="a"></param>
/// <param name="b"></param>
/// <returns></returns>
public static double operator *(Point3D a, Point3D b)
{
return (a.X * b.X) + (a.Y * b.Y) + (a.Z * b.Z);
}
public static Point3D operator /(Point3D a, double scalar)
{
if (scalar == 0)
{
throw new DivideByZeroException("Cannot divide by zero.");
}
return new Point3D(a.X / scalar, a.Y / scalar, a.Z / scalar);
}
/// <summary>
/// 向量积,^是按位异或运算符,重载它用于表示向量积
/// </summary>
/// <param name="a"></param>
/// <param name="b"></param>
/// <returns></returns>
public static Point3D operator ^(Point3D a, Point3D b)
{
return new Point3D(
a.Y * b.Z - a.Z * b.Y, // X分量
a.Z * b.X - a.X * b.Z, // Y分量
a.X * b.Y - a.Y * b.X // Z分量
);
}
/// <summary>
/// 计算向量的模
/// </summary>
/// <returns></returns>
public double Magnitude()
{
return Math.Sqrt(X * X + Y * Y + Z * Z);
}
/// <summary>
/// 获取单位向量
/// </summary>
/// <returns></returns>
/// <exception cref="InvalidOperationException"></exception>
public Point3D Normalize()
{
double magnitude = Magnitude();
if (magnitude == 0)
{
throw new InvalidOperationException("Cannot normalize a zero vector.");
}
return this * (1 / magnitude);
}
/// <summary>
/// 计算向量之间的夹角(弧度)
/// </summary>
/// <param name="a"></param>
/// <param name="b"></param>
/// <returns></returns>
public static double AngleBetween(Point3D a, Point3D b)
{
double dotProduct = a * b;
double magnitudeA = a.Magnitude();
double magnitudeB = b.Magnitude();
return Math.Acos(dotProduct / (magnitudeA * magnitudeB));
}
/// <summary>
/// 计算向量在另一个向量上的投影
/// </summary>
/// <param name="b"></param>
/// <returns></returns>
public Point3D ProjectOnto(Point3D b)
{
double scalarProjection = (this * b) / (b.Magnitude() * b.Magnitude());
return b * scalarProjection;
}
/// <summary>
/// 计算点到向量的垂直向量
/// </summary>
/// <param name="v"></param>
/// <param name="point"></param>
/// <returns></returns>
public Point3D GetProjectVector(Point3D point)
{
var v = this;
// 计算点 P 到向量 v 的投影向量 p
double dotProduct = v * point;
double magnitudeSquared = v * v;
var p = v * (dotProduct / magnitudeSquared);
// 计算垂直向量 n
var n = point - p;
return n;
}
/// <summary>
/// 向量的反向
/// </summary>
/// <returns></returns>
public Point3D Negative()
{
return new Point3D(-X, -Y, -Z);
}
private static bool IsAlmostEqualTo(double val, double compareValue, double tolerance = 1E-7)
{
return Math.Abs(val - compareValue) < tolerance;
}
public bool IsAlmostEqualTo(Point3D other)
{
return IsAlmostEqualTo(this.X, other.X) && IsAlmostEqualTo(this.Y, other.Y) && IsAlmostEqualTo(this.Z, other.Z);
}
}