11

I read that the Math.Pow implementation is pretty complicated to be able to handle fractional powers. Why isn't there a version that takes an int for the exponent to make a faster version when you don't need fractional powers?

Joan Venge
  • 315,713
  • 212
  • 479
  • 689
  • 2
    Check out this link on SO: http://stackoverflow.com/questions/383587/how-do-you-do-integer-exponentiation-in-c – paulsm4 Aug 02 '11 at 21:49
  • Thanks but would it be fast as a MS' version? Because they use an external call for their Pow method. – Joan Venge Aug 02 '11 at 21:53
  • external calls are not directly a guarantee for speed. – H H Aug 02 '11 at 21:55
  • Thanks Henk, I assumed they wanted to write it in C++ to make it faster. What other reasons would there be to do that for this case? – Joan Venge Aug 02 '11 at 21:57
  • I was talking to a graphics programmer here and he said the implementation to handle fractional powers is much more complicated than just multiplying values, so I assumed I get hit by the same performance penalty even when my exponent is not fractional. – Joan Venge Aug 02 '11 at 22:00
  • http://stackoverflow.com/questions/2398442/why-isnt-int-powint-base-int-exponent-in-the-standard-c-libraries – phuclv Apr 22 '15 at 05:07

4 Answers4

6

Because you'd just need to convert it back into a float to multiply it against the logarithm of the base.

nm = em × ln n

Zombo
  • 1
  • 62
  • 391
  • 407
Ignacio Vazquez-Abrams
  • 776,304
  • 153
  • 1,341
  • 1,358
0

For a compiler it is only worthwhile to optimize by converting to a series of multiplies, if the exponent is constant. In which case you can write x*x or x*x*x yourself.

Edit: So if you want to avoid your math is done by the Math.Pow implementation (which uses exponent functions), just don't call it. If Math.Pow would be added for integers, the compiler would have figure out from how it is called if it should emit code for multiplication (if n is constant and small) or the default using exponent functions. That is non-trivial work for a compiler, and there would be no gain in terms of performance.

  • So you think it would optimize if I do Math.Pow (3, 5)? The call is external so I can't see the code. – Joan Venge Aug 02 '11 at 21:55
  • 1
    This utterly misses the point. `Math.Pow` doesn't do a series of multiplications. And even if it did, the library code behind it would use intermediate values even if the exponent was not known at compile time. – David Heffernan Aug 02 '11 at 21:57
0

I don't think that fast math functions was their first priority when they programmed them (see Why is Math.DivRem so inefficient). They could use a expotentiation by square that would be faster, at least for small exponents.

However because floating point is subject to rounding providing 2 different inplementations could mean different results, e.g. for pow(5.9,7) than for pow(5.9,7.0), which may be undesirable in some cases.

Community
  • 1
  • 1
ggf31416
  • 3,582
  • 1
  • 25
  • 26
  • What level of accuracy is guaranteed for the "pow" function? Guaranteeing precision within 0.5625ulp when raising to an integer power is a little tricky, but guaranteeing it when using exp(ln(base)\*pow) is even harder. Too C sufficiently botched extended-precision support that such types aren't generally available, since they'd make it much easier to yield a result accurate to `double` precision. – supercat Sep 16 '15 at 18:27
-4

Well, you could write your own (in C):

int intPow(int a,int b){
  int answer = a;
  int i;
  for(i=0;i<b-1;i++)
    answer *= a;
  return answer;
}
Chris Gregg
  • 2,376
  • 16
  • 30