Escreva uma função int fat ( int n ) que recebe
e retorna o fatorial de
.
Passo 1
O enunciado pede uma função com a assinatura
que recebe um inteiro
e retorna o fatorial de
.
Informações dadas e o que precisa ser entregue:
Informações dadas e o que precisa ser entregue:
- A função deve receber um inteiro
. - A função deve retornar o fatorial de
, isto é . - Não foram especificadas restrições sobre valores negativos ou limites superiores; preciso definir um comportamento razoável para esses casos.
Passo 2
O que é fatorial? Vou explicar devagar e com exemplos.
- Por definição, para um inteiro não negativo
:
- Caso especial:
.
Exemplo concreto:.
Passo 3
Decisão do método de implementação (iterativo ou recursivo) — vou justificar:
- Recursão usa a relação
. É elegante, mas em C pode causar estouro de pilha para grande e tem overhead de chamadas de função. - Iterativo (laço) é simples, rápido, fácil de entender e não sofre com profundidade de chamada. Para um exercício básico e uma função que retorna um
, iterativo é a escolha mais prática.
Portanto vou implementar de forma iterativa.
Passo 4
Tratamento de casos especiais e limites:
- Para
: o fatorial não está definido em inteiros negativos. Vou escolher um indicador de erro simples: retornar . (Explicação: como um fator positivo mínimo é , retornar sinaliza erro; poderia também lançar erro, usar unsignedou errno, mas o enunciado pede apenas uma função simples.) - Para
: retorno (pela definição). - Observação sobre overflow: tipo
em C normalmente tem 32 bits com máximo . O maior com cabendo num é , pois e já extrapola o limite. Vou adicionar uma verificação simples: se retorno para indicar que o resultado não cabe num .
Passo 5
Algoritmo passo a passo (em linguagem natural) para
não negativo e
:
- Inicializar
. - Para cada inteiro
de até (inclusive), fazer . - Ao final, retornar
.
Esse procedimento calcula exatamente
, porque multiplica todos os inteiros de
a
(com
já multiplicado ao inicializar com
).
Passo 6
Complexidade e comportamento:
- Complexidade de tempo:
multiplicações. - Complexidade de espaço:
, uso constante de memória extra. - Para
fora do intervalo tratado (negativos ou ), a função retorna para sinalizar erro/overflow.
Passo 7
Exemplo manual (para checar mentalmente): calcular
com o algoritmo iterativo:
- iniciar
- i=2:
- i=3:
- i=4:
- i=5:
- retorna
, que é . Isso confirma o procedimento.
Passo 8
Observações finais antes do código:
- A função abaixo segue a assinatura pedida
. - Ela trata
e retornando como indicação de erro/overflow. - Para usos em que se deseja suportar
maiores, usar tipos maiores ( ou bibliotecas de inteiros grandes) ou retornar outro sinalizador de erro seria necessário.
Resposta
int fat ( int n ) {
if (n < 0) return 0; /* fatorial indefinido para negativos -> sinaliza erro /
if (n > 12) return 0; / evita overflow do int (13! não cabe em 32-bit signed) */
int resultado = 1;
for (int i = 2; i <= n; ++i) {
resultado *= i;
}
return resultado;
}
if (n < 0) return 0; /* fatorial indefinido para negativos -> sinaliza erro /
if (n > 12) return 0; / evita overflow do int (13! não cabe em 32-bit signed) */
int resultado = 1;
for (int i = 2; i <= n; ++i) {
resultado *= i;
}
return resultado;
}