Alguma vez você já precisou fazer a operação de potenciação em C++ e percebeu que a seguinte operação não funciona?
// Como fazer potência em C++? int quadradoDoValor = x^2;
Se sim, bem-vindo ao clube! Quase todo mundo deve ter tentado fazer potência em C++ usando o “chapéu” (^) e percebeu que isso não funciona – e que não faz o que você quer. Mas aí, se o chapéu não funciona, como é que se faz potência em C++? Continue lendo para descobrir (ou veja o vídeo abaixo, se preferir).
Função pow() da biblioteca cmath
Felizmente, a biblioteca cmath do C++ fornece uma função que faz exatamente o que precisamos: a função pow
. Ela recebe dois argumentos: base e expoente, e retorna o valor da base elevada ao expoente. Simples, não?
std::pow(base, exp)
Parâmetros
base – base da potência de tipo inteiro ou ponto-flutuante (float, double, long double etc.)
exp – expoente da potência de de tipo inteiro ou ponto-flutuante
Retorno
Um número de tipo inteiro ou ponto-flutuante (dependendo do tipo dos parâmetros base e exp)
Exemplo 1: Como calcular potência em C++ – função pow
Vejamos a seguir alguns exemplos de uso da função pow
que eu tomei diretamente do site CppReference (da versão em inglês).
/**************************************** * Exemplo #1 - Como calcular potencia em C++ * exemplos de uso da funcao pow ****************************************/ #include <cmath> #include <cstring> #include <iostream> int main() { // Uso típico std::cout << "1) pow(2, 10) = " << std::pow(2, 10) << '\n' << "2) pow(2, 0.5) = " << std::pow(2, 0.5) << '\n' << "3) pow(-2, -3) = " << std::pow(-2, -3) << '\n'; // Uso com valores especiais std::cout << "4) pow(-1, NAN) = " << std::pow(-1, NAN) << '\n' << "5) pow(+1, NAN) = " << std::pow(+1, NAN) << '\n' << "6) pow(INFINITY, 2) = " << std::pow(INFINITY, 2) << '\n' << "7) pow(INFINITY, -1) = " << std::pow(INFINITY, -1) << '\n'; }
Como vemos no exemplo 1, o uso da função pow é muito simples, mas há algo a se notar: é preciso escrever std::pow
, e não apenas pow
, porque a função pow é definida no header <cmath>
dentro do namespace std, ao invés de ser declarada no escopo global do programa (se quiser relembrar o que são namespaces e escopos local e global, visite nosso artigo sobre o assunto).
Nos 3 primeiros couts do exemplo 1, a função pow é usada de modo “ordinário”, ou seja, todos os valores de base e expoente utilizados resultam em uma saída “normal” da função – ou seja, o resultado da potência nesses 3 casos é um somente um número.
Macros NAN e INFINITY
Já nos 4 últimos exemplos, vemos dois valores estranhos: NAN
e INFINITY
. Ambos são macros definidas no header <cmath>
que servem para representar valores numéricos “especiais”. Os seus significados estão listados a seguir:
- NAN – representa todos os valores não-numéricos (o acrônimo significa Not A Number, em inglês, ou “Não é um número”, em tradução direta para o português).
- INFINITY – representa o valor infinito.
Como vemos nos couts 4 e 6, a saída do pow também pode ter os valores nan
e infinity
, o que nos dá mais flexibilidade na hora de lidar com casos especiais, pois que podemos escrever algo assim:
/************************************************** * Exemplo #2 - Como calcular potencia em C++ * exemplos de tratamento dos casos especiais do pow ***************************************************/ auto result = std::pow(x, y); if (result == INFINITY) { // Faca algo } else if (result == NAN) { // Faca outra coisa } else { // Faca ainda outra coisa }
Use pow da biblioteca cmath, não da biblioteca math
Talvez você tenha decoberto pesquisando na internet que existem duas versões da função pow: uma declarada no header <cmath> (a que usei nos meus exemplos), e outra declarada no header <math.h>. Se você não sabia, não tem problema, talvez seja até melhor: isso pode ter te poupado carregar uma dúvida difícil de se elucidar. Mas não se preocupe, eu vou explicar brevemente qual é a diferença entre as duas e dizer porque você deve usar o pow do <cmath>.
Qual é, então, a diferença entre as duas? Nenhuma! As duas funções servem para a mesma coisa e calculam potências da mesma maneira. Por que existem duas, então? A função pow do <math.h> é na verdade uma função da linguagem C, e não do C++, e esse header (assim como outros que terminam em .h) existe para se manter a compatibilidade do C++ com o C. Além disso, <math.h> declara a maioria das funções e elementos no escopo global, podendo também declarar alguns símbolos no namespace std (isso depende do compilador).
Já a função pow do header <cmath> (esse é o equivalente – uma espécie de cópia – do header <math.h>, mas próprio da linguagem C++) declara a maioria dos símbolos (incluindo a função pow) no namespace std, podendo declarar também alguns símbolos no escopo global (isso também depende do compilador, assim como no caso da função pow do <math.h>).
Sabendo disso, para se padronizar a declaração das funções “de base” da linguagem C++ no namespace std, o comitê do C++ decidiu descontinuar (deprecate, em inglês) o header <math.h>. Assim, a recomendação é que se utilize o header <cmath> ao invés daquele para obter acesso à função pow.
Conclusão
Nesse artigo vimos como fazer uma operação de potenciação em C++ usando a função pow() do header <cmath> – e não do <math.h>, que é um header do C que existe por razões de compatibilidade. Mostrei que a sintaxe do pow() é bastante simples, e a função recebe apenas dois argumentos: a base e o expoente da operação de potencia. Para ajudar a entendermos como se calcular potência em C++ usando o pow, mostrei alguns casos típicos e especiais no exemplo #1, e dei uma sugestão de como se pode lidar com o resultado da operação para os valores especiais nan e inifinity.
Vimos ainda que a função pow() é declarada no namespace std no header <cmath>, enquanto no <math.h> a função é declarada no escopo global. Apesar disso, descobrimos que as funções de ambos os headers fazem a mesma coisa.
Referências
- Professional C++, de Marc Gregoire;
- C++ Primer, de Stanley B. Lipman.
Gostou do artigo? Então inscreva-se na nossa newsletter para não perder nenhum dos nossos artigos 🙂
Sou apaixonado por tecnologia, literatura e também filosofia. O cultivo dessas paixões ao longo da minha trajetória me inspiraram a compartilhar aquilo que aprendo com os outros da maneira mais clara que eu possa. Sou formado em Engenharia Elétrica no Brasil, e também sou engenheiro formado na França. Trabalho atualmente como programador C++ em uma multinacional francesa, uma das maiores empresas de TI do mundo.