Single.Epsilon 字段

定义

表示大于零的最小正 Single 值。Represents the smallest positive Single value that is greater than zero. 此字段为常数。This field is constant.

public: float Epsilon = 1.401298E-45;
public const float Epsilon = 1.401298E-45;
val mutable Epsilon : single
Public Const Epsilon As Single  = 1.401298E-45

字段值

Single

注解

Epsilon如果实例的值为零,则属性的值将反映 Single 数值操作或比较中重要的最小正值 SingleThe value of the Epsilon property reflects the smallest positive Single value that is significant in numeric operations or comparisons when the value of the Single instance is zero. 例如,下面的代码显示零和被 Epsilon 视为不相等的值,而零和一半的值被 Epsilon 视为相等。For example, the following code shows that zero and Epsilon are considered to be unequal values, whereas zero and half the value of Epsilon are considered to be equal.

using System;

public class Example
{
   public static void Main()
   {
      float[] values = { 0f, Single.Epsilon, Single.Epsilon * .5f };
      
      for (int ctr = 0; ctr <= values.Length - 2; ctr++)
      {
         for (int ctr2 = ctr + 1; ctr2 <= values.Length - 1; ctr2++)
         {
            Console.WriteLine("{0:r} = {1:r}: {2}", 
                              values[ctr], values[ctr2],  
                              values[ctr].Equals(values[ctr2]));
         }
         Console.WriteLine();
      }      
   }
}
// The example displays the following output:
//       0 = 1.401298E-45: False
//       0 = 0: True
//       
//       1.401298E-45 = 0: False
Module Example
   Public Sub Main()
      Dim values() As Single = { 0, Single.Epsilon, Single.Epsilon * .5 }
      
      For ctr As Integer = 0 To values.Length - 2
         For ctr2 As Integer = ctr + 1 To values.Length - 1
            Console.WriteLine("{0:r} = {1:r}: {2}", _
                              values(ctr), values(ctr2), _ 
                              values(ctr).Equals(values(ctr2)))
         Next
         Console.WriteLine()
      Next      
   End Sub
End Module
' The example displays the following output:
'       0 = 1.401298E-45: False
'       0 = 0: True
'       
'       1.401298E-45 = 0: False

更准确地说,单精度浮点格式由符号、23位尾数或有效位数以及8位指数组成。More precisely, the single-precision floating-point format consists of a sign, a 23-bit mantissa or significand, and an 8-bit exponent. 如下面的示例所示,零的指数为-126,尾数为0。As the following example shows, zero has an exponent of -126 and a mantissa of 0. Epsilon 的指数为-126,尾数为1。Epsilon has an exponent of -126 and a mantissa of 1. 这意味着, Single.Epsilon 为大于零的最小正值, Single 表示 Single 其指数为-126 的的最小可能值和最小可能增量。This means that Single.Epsilon is the smallest positive Single value that is greater than zero and represents the smallest possible value and the smallest possible increment for a Single whose exponent is -126.

using System;

public class Example
{
   public static void Main()
   {
      float[] values = { 0.0f, Single.Epsilon };
      foreach (var value in values) {
         Console.WriteLine(GetComponentParts(value));
         Console.WriteLine();
      }   
   }

   private static string GetComponentParts(float value)
   {
      string result = String.Format("{0:R}: ", value);
      int indent = result.Length;

      // Convert the single to a 4-byte array.
      byte[] bytes = BitConverter.GetBytes(value);
      int formattedSingle = BitConverter.ToInt32(bytes, 0);
      
      // Get the sign bit (byte 3, bit 7).
      result += String.Format("Sign: {0}\n", 
                              (formattedSingle >> 31) != 0 ? "1 (-)" : "0 (+)");

      // Get the exponent (byte 2 bit 7 to byte 3, bits 6)
      int exponent =  (formattedSingle >> 23) & 0x000000FF;
      int adjustment = (exponent != 0) ? 127 : 126;
      result += String.Format("{0}Exponent: 0x{1:X4} ({1})\n", new String(' ', indent), exponent - adjustment);

      // Get the significand (bits 0-22)
      long significand = exponent != 0 ? 
                         ((formattedSingle & 0x007FFFFF) | 0x800000) : 
                         (formattedSingle & 0x007FFFFF); 
      result += String.Format("{0}Mantissa: 0x{1:X13}\n", new String(' ', indent), significand);    
      return result;   
   }
}
//       // The example displays the following output:
//       0: Sign: 0 (+)
//          Exponent: 0xFFFFFF82 (-126)
//          Mantissa: 0x0000000000000
//       
//       
//       1.401298E-45: Sign: 0 (+)
//                     Exponent: 0xFFFFFF82 (-126)
//                     Mantissa: 0x0000000000001
Module Example
   Public Sub Main()
      Dim values() As Single = { 0.0, Single.Epsilon }
      For Each value In values
         Console.WriteLine(GetComponentParts(value))
         Console.WriteLine()
      Next   
   End Sub

   Private Function GetComponentParts(value As Single) As String
      Dim result As String =  String.Format("{0:R}: ", value)
      Dim indent As Integer =  result.Length

      ' Convert the single to an 8-byte array.
      Dim bytes() As Byte = BitConverter.GetBytes(value)
      Dim formattedSingle As Integer = BitConverter.ToInt32(bytes, 0)

      ' Get the sign bit (byte 3, bit 7).
      result += String.Format("Sign: {0}{1}", 
                              If(formattedSingle >> 31 <> 0, "1 (-)", "0 (+)"),
                              vbCrLf)

      ' Get the exponent (byte 2 bit 7 to byte 3, bits 6)
      Dim exponent As Integer =  (formattedSingle >> 23) And &h000000FF
      Dim adjustment As Integer = If(exponent <> 0, 127, 126)
      result += String.Format("{0}Exponent: 0x{1:X4} ({1}){2}", 
                              New String(" "c, indent), exponent - adjustment,
                              vbCrLf)

      ' Get the significand (bits 0-22)
      Dim significand As Long =  If(exponent <> 0, 
                         (formattedSingle And &h007FFFFF) Or &h800000, 
                         formattedSingle And &h007FFFFF) 
      result += String.Format("{0}Mantissa: 0x{1:X13}{2}", 
                              New String(" "c, indent), significand, vbCrLf)    

      Return result   
   End Function
End Module
' The example displays the following output:
'       0: Sign: 0 (+)
'          Exponent: 0xFFFFFF82 (-126)
'          Mantissa: 0x0000000000000
'       
'       
'       1.401298E-45: Sign: 0 (+)
'                     Exponent: 0xFFFFFF82 (-126)
'                     Mantissa: 0x0000000000001

但是, Epsilon 属性不是类型的精度的常规度量值 Single ; 它仅适用于值为 Single 零的实例。However, the Epsilon property is not a general measure of precision of the Single type; it applies only to Single instances that have a value of zero.

备注

此属性的值 Epsilon 不等效于计算机 epsilon,后者表示相对错误的上限,原因是浮点算法中的舍入。The value of the Epsilon property is not equivalent to machine epsilon, which represents the upper bound of the relative error due to rounding in floating-point arithmetic.

此常量的值为 1.4 e-45。The value of this constant is 1.4e-45.

两个显然等效的浮点数可能不相等,因为其最小有效位之间存在差异。Two apparently equivalent floating-point numbers might not compare equal because of differences in their least significant digits. 例如,c # 表达式不 (float)1/3 == (float)0.33333 比较相等,因为左侧的除法运算具有最大的精度,而右侧的常数仅精确到指定的位数。For example, the C# expression, (float)1/3 == (float)0.33333, does not compare equal because the division operation on the left side has maximum precision while the constant on the right side is precise only to the specified digits. 如果您创建了一个自定义算法来确定是否可以将两个浮点数视为相等,则必须使用大于该常数的值, Epsilon 以便为两个要视为相等的两个值建立可接受的绝对差值。If you create a custom algorithm that determines whether two floating-point numbers can be considered equal, you must use a value that is greater than the Epsilon constant to establish the acceptable absolute margin of difference for the two values to be considered equal. (通常情况下,差值幅度比更多 Epsilon 。 ) (Typically, that margin of difference is many times greater than Epsilon.)

平台说明Platform Notes

ARM 系统上的 Epsilon 常量值太小,无法检测到,因此它等于零。On ARM systems, the value of the Epsilon constant is too small to be detected, so it equates to zero. 可以改为定义等于 1.175494351 E-38 的备用 epsilon 值。You can define an alternative epsilon value that equals 1.175494351E-38 instead.

适用于