与点(point)相比,PointF 是否会四舍五入?

4

我需要按以下方式比较一个PointF和一个Point:

PointF myPointF = new PointF(1.1,1.1);
Point myPoint = new Point(1,1);
bool Equal = (myPointF == myPoint);

但我想知道以下哪些是真实的,或者比较实际发生了什么不同的情况:
1. myPoint 首先被转换为 PointF 2. myPointF 首先被四舍五入到 Point 3. 一些完全不同和不可预测的情况
可以编写一个测试,但我想在文档中看到保证的答案。
此外,存在从 Point 到 PointF 的隐式转换,而不存在相反的转换,所以我认为这足以说明 Point 被转换为 PointF,但我不能确定。同时,这里有一个从 Point 到 PointF 的隐式转换,而不存在相反的转换,所以我认为这足以说明 Point 被转换为 PointF,但我不能确定。

你尝试过反向工程代码吗? - nothrow
1
你的想法是正确的,任何隐式发生的转换都不会涉及到数据丢失,所以 int 类型可以转换为 float 类型。 - prthrokz
2
就我个人而言,我更相信实际测试的结果,而不是文档中所说的。 - Matt Burland
@Yossarian 你是指编译成中间语言吗?我知道有一种中间语言,但我不熟悉它。 - AppFzx
2个回答

4
使用LinqPad很容易查看IL以了解情况。基本上,Point被转换为PointF,然后为PointF调用==等于方法。

例如,使用以下代码:
System.Drawing.PointF myPointF = new System.Drawing.PointF(1.1f ,1.1f);
System.Drawing.Point myPoint = new System.Drawing.Point(1,1);
bool equal = (myPointF == myPoint);
Console.WriteLine(equal);

生成以下IL代码:
IL_0001:  ldloca.s    00 // myPointF
IL_0003:  ldc.r4      CD CC 8C 3F 
IL_0008:  ldc.r4      CD CC 8C 3F 
IL_000D:  call        System.Drawing.PointF..ctor
IL_0012:  nop         
IL_0013:  ldloca.s    01 // myPoint
IL_0015:  ldc.i4.1    
IL_0016:  ldc.i4.1    
IL_0017:  call        System.Drawing.Point..ctor
IL_001C:  nop         
IL_001D:  ldloc.0     // myPointF
IL_001E:  ldloc.1     // myPoint
IL_001F:  call        System.Drawing.Point.op_Implicit   //<- convert Point to PointF
IL_0024:  call        System.Drawing.PointF.op_Equality  //<- PointF equality
IL_0029:  stloc.2     // equal
IL_002A:  ldloc.2     // equal
IL_002B:  call        System.Console.WriteLine

如果您使用ILSpy,您可以找到Point.op_ImplicitPointF.op_Equality的内容。
// System.Drawing.Point
public static implicit operator PointF(Point p)
{
    return new PointF((float)p.X, (float)p.Y);
}

// System.Drawing.PointF
public static bool operator ==(PointF left, PointF right)
{
    return left.X == right.X && left.Y == right.Y;
}

这表明当将Point转换为PointF时,int值会转换为float值,然后比较原始PointF实例和转换后的PointF实例的float值。


完美。比我所期望的更深入。 - AppFzx

3
让我们看一下ildasm.exe显示的内容:
IL_001f:  call       valuetype [System.Drawing]System.Drawing.PointF [System.Drawing]System.Drawing.Point::op_Implicit(valuetype  [System.Drawing]System.Drawing.Point)
IL_0024:  call       bool [System.Drawing]System.Drawing.PointF::op_Equality(valuetype [System.Drawing]System.Drawing.PointF,valuetype [System.Drawing]System.Drawing.PointF)

所以,是的。在比较中,Point会被视为一个PointF。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接