搜索
bottom↓
回复: 3

John Carmack的sqrt函数为什么计算结果与系统库sqrt的结果不一致

[复制链接]

出0入0汤圆

发表于 2015-1-23 16:02:42 | 显示全部楼层 |阅读模式
本帖最后由 xf331785508 于 2015-1-23 16:05 编辑

如题,网上找的Carmack的神奇函数,函数体如下:
  1. static float Q_rsqrt( float x )
  2. {
  3.     long i;
  4.     float x2, y;
  5.     const float threehalfs = 1.5F;

  6.      printf("Q_rsqrt start: x=%-6.7f\n", x);

  7.     x2 = x * 0.5F;
  8.     y   = x;
  9.     i   = * ( long * ) &y;   // evil floating point bit level hacking
  10.     i   = 0x5f3759df - ( i >> 1 ); // what the fuck?
  11.     y   = * ( float * ) &i;
  12.     y   = y * ( threehalfs - ( x2 * y * y ) ); // 1st iteration
  13.    

  14.     #ifndef Q3_VM
  15.     #ifdef __linux__
  16.          assert( !isnan(y) ); // bk010122 - FPE?
  17.     #endif
  18.     #endif

  19.         printf("Q_rsqrt end: y=%-6.5f\n", y);
  20.     return y;
  21. }
复制代码


最简化的函数体如下:
  1. static float CarmackSqrt (float x)
  2. {
  3.         float xhalf = 0.5f*x;
  4.         int i = *(int*)&x; // get bits for floating VALUE

  5.         printf("x=%-6.7f\n", x);

  6.        i = 0x5f3759df- (i>>1); // gives initial guess y0
  7.        x = *(float*)&i; // convert bits BACK to float
  8.        x = x*(1.5f-xhalf*x*x); // Newton step, repeating increases accuracy
  9.        printf("x=%-6.3f\n", x);
  10.        x = x*(1.5f-xhalf*x*x); // Newton step, repeating increases accuracy
  11.        printf("x=%-6.3f\n", x);
  12.        x = x*(1.5f-xhalf*x*x); // Newton step, repeating increases accuracy
  13.        printf("x=%-6.3f\n", x);

  14.        return x;
复制代码


我用EXCEL的计算结果与用库函数sqrtf计算的结果一致,但利用上述函数就错的很大,怎么回事呢。
------------------------------------------
测试算法平台: CPU i3-2120   VC++ 6.0 控制台工程,输出结果到文本文件。截图即文本文件结果。

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?注册

x

阿莫论坛20周年了!感谢大家的支持与爱护!!

你熬了10碗粥,别人一桶水倒进去,淘走90碗,剩下10碗给你,你看似没亏,其实你那10碗已经没有之前的裹腹了,人家的一桶水换90碗,继续卖。说白了,通货膨胀就是,你的钱是挣来的,他的钱是印来的,掺和在一起,你的钱就贬值了。

出0入0汤圆

 楼主| 发表于 2015-1-23 16:34:28 | 显示全部楼层
  1. void TestSqrt(void)
  2. {
  3. unsigned char i = 0;
  4. float measureValue[] = {
  5.   2.132f, 5.043f, 4.563f, 0.503f, 7.223f,
  6.   2.181f, 5.247f, 3.799f, 0.536f, 7.163f,
  7.   2.152f, 5.201f, 3.912f, 0.528f, 7.189f,
  8.   2.142f, 5.178f, 3.582f, 0.528f, 7.165f,
  9.   2.181f, 5.316f, 3.453f, 0.547f, 7.143f,
  10.   2.171f, 5.340f, 3.378f, 0.547f, 7.169f};

  11. printf("==============测试Carmack函数=====================\n");
  12.   for( i = 0; i < COUNTOF(measureValue); i++ )
  13.   {
  14.           printf("Source data is %-6.6f,\nCarmack's result is: %-6.6f,\nSystem's  result is: %-6.6f\n",
  15.                      measureValue[i], CarmackSqrt(measureValue[i]), sqrtf(measureValue[i]));
  16.           printf("\n");
  17.   }
  18.   printf("==============测试Carmack函数结束=================\n");
  19. }
  20. ==============测试Carmack函数=====================
  21. Source data is 2.132000,
  22. Carmack's result is: 0.684867,
  23. System's  result is: 1.460137

  24. Source data is 5.043000,
  25. Carmack's result is: 0.445303,
  26. System's  result is: 2.245663

  27. Source data is 4.563000,
  28. Carmack's result is: 0.468139,
  29. System's  result is: 2.136118

  30. Source data is 0.503000,
  31. Carmack's result is: 1.409990,
  32. System's  result is: 0.709225

  33. Source data is 7.223000,
  34. Carmack's result is: 0.372084,
  35. System's  result is: 2.687564

  36. Source data is 2.181000,
  37. Carmack's result is: 0.677130,
  38. System's  result is: 1.476821

  39. Source data is 5.247000,
  40. Carmack's result is: 0.436561,
  41. System's  result is: 2.290633

  42. Source data is 3.799000,
  43. Carmack's result is: 0.513057,
  44. System's  result is: 1.949102

  45. Source data is 0.536000,
  46. Carmack's result is: 1.365896,
  47. System's  result is: 0.732120

  48. Source data is 7.163000,
  49. Carmack's result is: 0.373639,
  50. System's  result is: 2.676378

  51. Source data is 2.152000,
  52. Carmack's result is: 0.681677,
  53. System's  result is: 1.466970

  54. Source data is 5.201000,
  55. Carmack's result is: 0.438487,
  56. System's  result is: 2.280570

  57. Source data is 3.912000,
  58. Carmack's result is: 0.505592,
  59. System's  result is: 1.977878

  60. Source data is 0.528000,
  61. Carmack's result is: 1.376205,
  62. System's  result is: 0.726636

  63. Source data is 7.189000,
  64. Carmack's result is: 0.372963,
  65. System's  result is: 2.681231

  66. Source data is 2.142000,
  67. Carmack's result is: 0.683267,
  68. System's  result is: 1.463557

  69. Source data is 5.178000,
  70. Carmack's result is: 0.439460,
  71. System's  result is: 2.275522

  72. Source data is 3.582000,
  73. Carmack's result is: 0.528369,
  74. System's  result is: 1.892617

  75. Source data is 0.528000,
  76. Carmack's result is: 1.376205,
  77. System's  result is: 0.726636

  78. Source data is 7.165000,
  79. Carmack's result is: 0.373587,
  80. System's  result is: 2.676752

  81. Source data is 2.181000,
  82. Carmack's result is: 0.677130,
  83. System's  result is: 1.476821

  84. Source data is 5.316000,
  85. Carmack's result is: 0.433718,
  86. System's  result is: 2.305645

  87. Source data is 3.453000,
  88. Carmack's result is: 0.538148,
  89. System's  result is: 1.858225

  90. Source data is 0.547000,
  91. Carmack's result is: 1.352092,
  92. System's  result is: 0.739594

  93. Source data is 7.143000,
  94. Carmack's result is: 0.374162,
  95. System's  result is: 2.672639

  96. Source data is 2.171000,
  97. Carmack's result is: 0.678688,
  98. System's  result is: 1.473431

  99. Source data is 5.340000,
  100. Carmack's result is: 0.432742,
  101. System's  result is: 2.310844

  102. Source data is 3.378000,
  103. Carmack's result is: 0.544089,
  104. System's  result is: 1.837934

  105. Source data is 0.547000,
  106. Carmack's result is: 1.352092,
  107. System's  result is: 0.739594

  108. Source data is 7.169000,
  109. Carmack's result is: 0.373483,
  110. System's  result is: 2.677499

  111. ==============测试Carmack函数结束=================
复制代码

出0入0汤圆

 楼主| 发表于 2015-1-23 16:44:41 | 显示全部楼层
呵呵,个人低级错误 ,返回值取倒就OK 了。

出0入0汤圆

发表于 2015-1-24 04:20:18 | 显示全部楼层
这是求isqrt not sqrt
回帖提示: 反政府言论将被立即封锁ID 在按“提交”前,请自问一下:我这样表达会给举报吗,会给自己惹麻烦吗? 另外:尽量不要使用Mark、顶等没有意义的回复。不得大量使用大字体和彩色字。【本论坛不允许直接上传手机拍摄图片,浪费大家下载带宽和论坛服务器空间,请压缩后(图片小于1兆)才上传。压缩方法可以在微信里面发给自己(不要勾选“原图),然后下载,就能得到压缩后的图片。注意:要连续压缩2次才能满足要求!!】。另外,手机版只能上传图片,要上传附件需要切换到电脑版(不需要使用电脑,手机上切换到电脑版就行,页面底部)。
您需要登录后才可以回帖 登录 | 注册

本版积分规则

手机版|Archiver|amobbs.com 阿莫电子技术论坛 ( 粤ICP备2022115958号, 版权所有:东莞阿莫电子贸易商行 创办于2004年 (公安交互式论坛备案:44190002001997 ) )

GMT+8, 2024-10-3 03:22

© Since 2004 www.amobbs.com, 原www.ourdev.cn, 原www.ouravr.com

快速回复 返回顶部 返回列表