C# 求C中直线与X轴的最小角度#

C# 求C中直线与X轴的最小角度#,c#,vector,angle,C#,Vector,Angle,假设我们通过减去两条直线的端点来定义两个向量 V1 = Pa - Pb; V2 = Pc - Pd; 我们将X轴定义为以下向量 var V = new System.Windows.Vector(1, 0); 我们如何知道两个向量V1和V2中哪一个与X轴的夹角最小。将两者归一化,并找到一个绝对值X较高的向量 或者,两个向量a和b之间的角度为arccos((a.x*b.x+a.y*b.y)/(a.Length*b.Length))(如果其中一个向量为零,则未定义)将两者归一化,并找到一个绝对值

假设我们通过减去两条直线的端点来定义两个向量

V1 = Pa - Pb;
V2 = Pc - Pd;
我们将X轴定义为以下向量

var V = new System.Windows.Vector(1, 0);

我们如何知道两个向量V1和V2中哪一个与X轴的夹角最小。

将两者归一化,并找到一个绝对值X较高的向量


或者,两个向量
a
b
之间的角度为
arccos((a.x*b.x+a.y*b.y)/(a.Length*b.Length))
(如果其中一个向量为零,则未定义)

将两者归一化,并找到一个绝对值较高的向量


或者,两个向量
a
b
之间的角度为
arccos((a.x*b.x+a.y*b.y)/(a.Length*b.Length))
(如果其中一个向量为零,则未定义)您有两个选项:您可以使用
AngleBetween
功能计算
V1
V
V2
V
之间的角度:

var angle1 = Vector.AngleBetween(V1,V);
var angle2 = Vector.AngleBetween(V2,V);

if (angle1 < angle2) {
    //V1 is closer to V
}else{
    //V2 is closer to V
}
我更喜欢第一种方法,因为
Normalize()
函数实际上会更改原始向量,因此如果以后要使用它们,则需要进行复制。您还可以使用第一个版本,以便将它们与任何其他向量
V
进行比较,而无需调整代码

编辑:实际上,第一个版本只选择与
V
向量成最小角度的向量,而与x轴成最小角度的向量。因此,如果您想与轴而不仅仅是矢量进行比较,则应使用绝对
x
y
值的
V1
V2
副本进行角度计算:

var ref1 = new System.Windows.Vector(Math.Abs(V1.X),Math.Abs(V1.Y));
var ref2 = new System.Windows.Vector(Math.Abs(V2.X),Math.Abs(V2.Y));
var angle1 = Vector.AngleBetween(ref1,V);
var angle2 = Vector.AngleBetween(ref2,V);

if (angle1 < angle2) {
    //V1 is closer to V
}else{
    //V2 is closer to V
}
var ref1=newsystem.Windows.Vector(Math.Abs(V1.X)、Math.Abs(V1.Y));
var ref2=newsystem.Windows.Vector(Math.Abs(V2.X)、Math.Abs(V2.Y));
var angle1=矢量之间的角度(参考文献1,V);
var angle2=矢量之间的角度(参考文献2,V);
如果(角度1<角度2){
//V1更接近V
}否则{
//V2更接近V
}

从这个角度来看,规范化方法可能是更好的选择。(但一定要在副本上调用
Normalize()

您有两个选项:您可以使用
AngleBetween
函数计算
V1
V
之间的角度:

var angle1 = Vector.AngleBetween(V1,V);
var angle2 = Vector.AngleBetween(V2,V);

if (angle1 < angle2) {
    //V1 is closer to V
}else{
    //V2 is closer to V
}
我更喜欢第一种方法,因为
Normalize()
函数实际上会更改原始向量,因此如果以后要使用它们,则需要进行复制。您还可以使用第一个版本,以便将它们与任何其他向量
V
进行比较,而无需调整代码

编辑:实际上,第一个版本只选择与
V
向量成最小角度的向量,而与x轴成最小角度的向量。因此,如果您想与轴而不仅仅是矢量进行比较,则应使用绝对
x
y
值的
V1
V2
副本进行角度计算:

var ref1 = new System.Windows.Vector(Math.Abs(V1.X),Math.Abs(V1.Y));
var ref2 = new System.Windows.Vector(Math.Abs(V2.X),Math.Abs(V2.Y));
var angle1 = Vector.AngleBetween(ref1,V);
var angle2 = Vector.AngleBetween(ref2,V);

if (angle1 < angle2) {
    //V1 is closer to V
}else{
    //V2 is closer to V
}
var ref1=newsystem.Windows.Vector(Math.Abs(V1.X)、Math.Abs(V1.Y));
var ref2=newsystem.Windows.Vector(Math.Abs(V2.X)、Math.Abs(V2.Y));
var angle1=矢量之间的角度(参考文献1,V);
var angle2=矢量之间的角度(参考文献2,V);
如果(角度1<角度2){
//V1更接近V
}否则{
//V2更接近V
}
从这个角度来看,规范化方法可能是更好的选择。(但一定要在副本上调用
Normalize()

双重比较(){
p0点=新点(0,0);
点p1=新点(100100);
点p2=新点(100,-100);
向量v0=新系统.Windows.Vector(1,0);
VarV1=p1-p0;
var v2=p2-p0;
var value1=向量。角度介于(v0,v1);//值=45
var value2=向量。角度介于(v0,v2)之间;//值=-45
value1=数学Abs(value1);
value2=数学Abs(value2);
/*或者,如果要比较角度的值
如果(值1<0)
值1+=360;
如果(值2<0)
值2+=360;
*/
返回Math.Min(值1,值2);
}
双重比较(){
p0点=新点(0,0);
点p1=新点(100100);
点p2=新点(100,-100);
向量v0=新系统.Windows.Vector(1,0);
VarV1=p1-p0;
var v2=p2-p0;
var value1=向量。角度介于(v0,v1);//值=45
var value2=向量。角度介于(v0,v2)之间;//值=-45
value1=数学Abs(value1);
value2=数学Abs(value2);
/*或者,如果要比较角度的值
如果(值1<0)
值1+=360;
如果(值2<0)
值2+=360;
*/
返回Math.Min(值1,值2);
}

检查以下解决方案。可能会满足您的查询。请将引用Windowsbase添加到项目中。非常重要

using System;
using System.Windows;

namespace Vectors
{

    class Program
    {

        static void Main(string[] args)
        {
            // Define Points
            Point Pa = new Point(5.0,1.0);
            Point Pb = new Point(10.0,3.0);
            Point Pc = new Point(7.0,10.0);
            Point Pd = new Point(1.0,3.0);
            Vector V1 = Pa - Pb;
            Vector V2 = Pc - Pd;

            Vector V = new Vector(1, 0);

            double Phi1 = Math.Atan2(V1.Y, V1.X)*180/Math.PI;
            double Phi2 = Math.Atan2(V2.Y, V2.X)*180/Math.PI;

            // Check for -ve angle and take 180 degree complement.
            Phi1 = (Phi1 >= 0) ? Phi1 : 180 + Phi1;
            Phi2 = (Phi2 >= 0) ? Phi2 : 180 + Phi2;

            if(Phi1<=Phi2)
            {
                Console.WriteLine("Vector V1 has a least angle");
            }
            else
            {
                Console.WriteLine("Vector V2 has a least angle");
            }
            Console.ReadLine();
        }
    }
}
使用系统;
使用System.Windows;
命名空间向量
{
班级计划
{
静态void Main(字符串[]参数)
{
//定义点
点Pa=新点(5.0,1.0);
点Pb=新点(10.0,3.0);
点Pc=新点(7.0,10.0);
点Pd=新点(1.0,3.0);
向量V1=Pa-Pb;
向量V2=Pc-Pd;
向量V=新向量(1,0);
双Phi1=数学Atan2(V1.Y,V1.X)*180/Math.PI;
双Phi2=数学Atan2(V2.Y,V2.X)*180/Math.PI;
//检查-ve角度并取180度补角。
Phi1=(Phi1>=0)?Phi1:180+Phi1;
Phi2=(Phi2>=0)?Phi2:180+Phi2;

如果(Phi1检查以下解决方案。可能会满足您的查询。将参考Windowsbase添加到项目中。非常重要

using System;
using System.Windows;

namespace Vectors
{

    class Program
    {

        static void Main(string[] args)
        {
            // Define Points
            Point Pa = new Point(5.0,1.0);
            Point Pb = new Point(10.0,3.0);
            Point Pc = new Point(7.0,10.0);
            Point Pd = new Point(1.0,3.0);
            Vector V1 = Pa - Pb;
            Vector V2 = Pc - Pd;

            Vector V = new Vector(1, 0);

            double Phi1 = Math.Atan2(V1.Y, V1.X)*180/Math.PI;
            double Phi2 = Math.Atan2(V2.Y, V2.X)*180/Math.PI;

            // Check for -ve angle and take 180 degree complement.
            Phi1 = (Phi1 >= 0) ? Phi1 : 180 + Phi1;
            Phi2 = (Phi2 >= 0) ? Phi2 : 180 + Phi2;

            if(Phi1<=Phi2)
            {
                Console.WriteLine("Vector V1 has a least angle");
            }
            else
            {
                Console.WriteLine("Vector V2 has a least angle");
            }
            Console.ReadLine();
        }
    }
}
使用系统;
使用System.Windows;
命名空间向量
{
班级计划
{
静态void Main(字符串[]参数)
{
//定义点
点Pa=新点(5.0