Как вы делаете возведение в степень в C? - PullRequest
48 голосов
/ 17 октября 2008

Я попробовал "x = y ** e", но это не сработало.

Ответы [ 7 ]

87 голосов
/ 17 октября 2008

использовать функцию pow (хотя требуется float с / double с).

man pow

   #include <math.h>

   double pow(double x, double y);
   float powf(float x, float y);
   long double powl(long double x, long double y);

EDIT: Кстати, для особого случая положительных целочисленных степеней 2 вы можете использовать сдвиг битов: (1 << x) будет равняться 2 степени x. Есть некоторые потенциальные ошибки с этим, но в целом это было бы правильно.

31 голосов
/ 17 октября 2008

Чтобы добавить к тому, что Эван сказал: C не имеет встроенного оператора для возведения в степень, потому что это не примитивная операция для большинства процессоров. Таким образом, он реализован как библиотечная функция.

Также для вычисления функции e ^ x вы можете использовать функции exp(double), expf(float) и expl(long double).

Обратите внимание, что вы не хотите использовать оператор ^, который является оператором побитового исключающего ИЛИ .

23 голосов
/ 17 октября 2008

pow работает только с числами с плавающей запятой (на самом деле double с). Если вы хотите получить полномочия целых чисел, а основание неизвестно, как показатель степени 2, вам придется бросить свои собственные.

Обычно тупой путь достаточно хорош.

int power(int base, unsigned int exp) {
    int i, result = 1;
    for (i = 0; i < exp; i++)
        result *= base;
    return result;
 }

Вот рекурсивное решение, которое занимает O(log n) пространство и время вместо простого O(1) пространство O(n) время:

int power(int base, int exp) {
    if (exp == 0)
        return 1;
    else if (exp % 2)
        return base * power(base, exp - 1);
    else {
        int temp = power(base, exp / 2);
        return temp * temp;
    }
}
6 голосов
/ 19 июля 2012

Как и в предыдущем ответе, он будет хорошо обрабатывать положительные и отрицательные целочисленные степени двойного числа.

double intpow(double a, int b)
{
  double r = 1.0;
  if (b < 0)
  {
    a = 1.0 / a;
    b = -b;
  }
  while (b)
  {
    if (b & 1)
      r *= a;
    a *= a;
    b >>= 1;
  }
  return r;
}
4 голосов
/ 18 октября 2008

Нерекурсивная версия функции не слишком сложна - здесь она для целых чисел:

long powi(long x, unsigned n)
{
    long p = x;
    long r = 1;

    while (n > 0)
    {
        if (n % 2 == 1)
            r *= p;
        p *= p;
        n /= 2;
    }

    return(r);
}

(Взломан из кода для возведения двойного значения в целую степень - пришлось удалить код, например, для работы с ответными ссылками.)

2 голосов
/ 09 января 2011
int power(int x,int y){
 int r=1;
 do{
  r*=r;
  if(y%2)
   r*=x;
 }while(y>>=1);
 return r;
};

(итерационный)

int power(int x,int y){
 return y?(y%2?x:1)*power(x*x,y>>1):1;
};

(если это должно быть рекурсивно)

imo, алгоритм определенно должен быть O (logn)

1 голос
/ 17 октября 2008

или вы можете просто написать степенную функцию с рекурсией в качестве дополнительного бонуса

int power(int x, int y){
      if(y == 0)
        return 1;
     return (x * power(x,y-1) );
    }

да, да, я знаю, что это менее эффективное пространство и временная сложность, но рекурсия просто веселее !!

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...