Math类的误区

无论刚入门的还是有一定AS3编程基础的,对Math类应该都不陌生了,但Math类的性能又知多少呢?请看下文吧。

1、Math.floor()
通俗的讲这是一个取整函数。
其实官方解释是:

返回由参数 val 指定的数字或表达式的下限值。 下限值是小于等于指定数字或表达式的最接近的整数。

性能测试:

  1. var num:Number = Math.PI;
  2. var length:int = 10000000;
  3. var time:int = getTimer();
  4. for(var i:int = 0; i < length; i ++){
  5.         Math.floor(num);
  6. }
  7. trace(getTimer() - time);
  8. // 结果:1865
复制代码
  1. var num:Number = Math.PI;
  2. var length:int = 10000000;
  3. var time:int = getTimer();
  4. for(var i:int = 0; i < length; i ++){
  5.         int(num);
  6. }
  7. trace(getTimer() - time);
  8. // 结果:69
复制代码

结果很明显,int比floor快,可能大家就要说了,那Adobe傻X写个这样接口干什么?其实这就是我想说的对于floor的使用误区。
仔细看官方解释,其实floor不是一个真正我们所理解的取整函数,他是去找最接近自己,且比自己小或者等于的整数,那这是什么意思呢?

  1. var num:Number = - Math.PI;
  2. trace(int(num));
  3. trace(Math.floor(num));
  4. // 结果1:-3
  5. // 结果2:-4
复制代码

这个例子很明确表示,当目标数字是负数时,int和floor所得出的结果不一样。
int()的官方解释:

将给定数字值转换成整数值。 从小数点处截断十进制值。

相信看到这,你已经很明白了。
但是实际上,如果你这样去使用int(),跟floor输出的结果相同:

  1. var num:Number = - Math.PI;
  2. var length:int = 10000000;
  3. var time:int = getTimer();
  4. for(var i:int = 0; i < length; i ++){
  5.         if(num < 0){
  6.                 int(num) - 1;
  7.         }else{
  8.                 int(num);
  9.         }
  10. }
  11. trace(getTimer() - time);
  12. // 结果:132
复制代码

 
2、Math.pow()
对于这个方法,我也不知道说什么好了,先看性能测试吧:

  1. var a:int = 3;
  2. var b:int = 4;
  3. var c:int = 5;
  4. var length:int = 10000000;
  5. var time:int = getTimer();
  6. for(var i:int = 0; i < length; i ++){
  7.         c * c == a * a + b * b;
  8. }
  9. trace(getTimer() - time);
  10. // 结果:95
复制代码
  1. var a:int = 3;
  2. var b:int = 4;
  3. var c:int = 5;
  4. var length:int = 10000000;
  5. var time:int = getTimer();
  6. for(var i:int = 0; i < length; i ++){
  7.         Math.pow(c,2) == Math.pow(a,2) + Math.pow(b,2);
  8. }
  9. trace(getTimer() - time);
  10. // 结果:7999
复制代码

勾三股四弦五大家应该比较多,但是用"*"乘法运算和pow的性能比较那是非常明显啊。
难道大家又想说Adobe傻逼了?这儿我为它平反吧。

  1. var num:Number = Math.PI;
  2. var length:int = 10000000;
  3. var time:int = getTimer();
  4. for(var i:int = 0; i < length; i ++){
  5.         Math.pow(num,10000);
  6. }
  7. trace(getTimer() - time);
  8. // 结果:6682
复制代码

先不说"*"乘法运算比pow快,就上面这段你能把它换算成使用"*"乘法运算吗?
而且pow其实是可以这样用的:(数学学得好都知道开方其实是可以转换成乘方来算的)

  1. trace(Math.pow(27,1/3));
  2. trace(Math.pow(256,1/4));
  3. trace(Math.pow(3125,1/5));
复制代码

而开方函数Adobe只提供了sqrt一个开平方根的接口(经测试Math.sqrt(9)比Math.pow(9,1/2)快,但开立方等就得靠pow了)。
 
3、Math.round()
这个方法跟floor一样的,先看性能测试:

  1. var num:int = Math.PI;
  2. var length:int = 10000000;
  3. var time:int = getTimer();
  4. for(var i:int = 0; i < length; i ++){
  5.         Math.round(num);
  6. }
  7. trace(getTimer() - time);
  8. // 结果:1931
复制代码
  1. var num:int = Math.PI;
  2. var length:int = 10000000;
  3. var time:int = getTimer();
  4. for(var i:int = 0; i < length; i ++){
  5.         int(num + 0.5)
  6. }
  7. trace(getTimer() - time);
  8. // 结果:68
复制代码

四舍五入其实加个0.5在取整,这样也是可以的,只不过用这个算法,存在跟第一个同样的问题,当目标数值为负时,两种方式结果不一样,需要加个判断,目标数值为负就把结果-1。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值