Ir para conteúdo


Revista PROGRAMAR - Edição 45 (Maio 2014): Download já disponível! Visita também o novo website da revista.

- - - - -

Factorial de um número


  • Este tópico está fechado Este tópico está fechado
18 respostas a este tópico

#1 Yana

Yana

    null

  • Membro
  • Pip
  • 23 mensagens

Publicado 20 de Julho de 2012 - 23:26

Boas, este é um pequeno script que criei,  calcula o factorial de um número dado pelo utilizador. É bastante simples mas foi o meu primeiro script em python e quem sabe, até pudera dar jeito a alguém (ou não :P ) .
. Código (Python):
def factorial(n):
if not isinstance(n, int):
     print "Fatorial é apenas defenido por números"
     return None
elif n < 0:
     print "Fatorial não é defenido por numeros negativos."
     return None
elif n == 0:
     return 1
else:
     return n * factorial(n - 1)
x = raw_input("Numero para calcular o factorial: " )
print "O factorial de", x, "é " ,factorial(int(x)), "."
raw_input()

Editado por thoga31, 20 de Julho de 2012 - 23:30.
GeSHi


#2 thoga31

thoga31

    Stack Overflow

  • Moderador
  • PipPipPipPipPipPipPip
  • 7229 mensagens

Publicado 20 de Julho de 2012 - 23:37

Está engraçado. Mas podes simplificar. O "Return" pode ser de qualquer tipo, pelo que, em vez de Prints e um Return None, ficará mais elegante algo deste género:

Código (Python):
return "Erro: ..."

O resultado final seria o seguinte:
Código (Python):
def fact(n):
    if not isinstance(n, int):
        return "Erro: input não é número."
    elif not (n >= 0):
        return "Erro: número negativo."
    elif (n == 0):
        return 1
    else:
        return n * fact(n - 1)

Utilização:
Código (Python):
>>> fact("ops!")
"Erro: input não é número."
>>> fact(-5)
"Erro: número negativo."
>>> fact(4)
24

Continua com o bom trabalho. É assim que se começa. ;)

Editado por thoga31, 20 de Julho de 2012 - 23:43.


#3 Yana

Yana

    null

  • Membro
  • Pip
  • 23 mensagens

Publicado 20 de Julho de 2012 - 23:44

Ver Mensagemthoga31, em 20 de Julho de 2012 - 23:37, disse:

Está engraçado. Mas podes simplificar. O "Return" pode ser de qualquer tipo, pelo que, em vez de Prints e um Return None, ficará mais elegante algo deste género:

Código (Python):
return "Erro: ..."

De seguida, quando avalias os números, podes fazer uma avaliação sucessiva com "elif".

O resultado final seria o seguinte:
Código (Python):
def fact(n):
        if not isinstance(n, int):
                return "Erro: input não é número."
        if not (n >= 0):
                return "Erro: número negativo."
        elif (n == 0):
                return 1
        else:
                return n * fact(n - 1)

Utilização:
Código (Python):
>>> fact("ops!")
"Erro: input não é número."
>>> fact(-5)
"Erro: número negativo."
>>> fact(4)
24

Continua com o bom trabalho. É assim que se começa. ;)
Obrigado, o return fica mais 'limpo'. O script ficou mais simples não preciso de por return none.

#4 pwseo

pwseo

    Unsigned User

  • Moderador
  • PipPipPipPipPipPip
  • 1143 mensagens

Publicado 21 de Julho de 2012 - 12:13

Sendo isto uma função recursiva, penso que é desnecessário verificar se o parâmetro passado é ou não um número (e se é ou não positivo).
Este tipo de verificações devem ser feitas antes da parte recursiva (nem que isso implique definir uma função dentro da função factorial).
Imaginem factorial(1000): logo após chamar a função, sabemos que o seu argumento é um número positivo... mas da forma que o código está escrito, também vamos fazer essas verificações para 999, 998, 997, até ao 0, apesar de sabermos que isso é implicitamente verdade.

#5 Yana

Yana

    null

  • Membro
  • Pip
  • 23 mensagens

Publicado 21 de Julho de 2012 - 13:50

Ver Mensagempwseo, em 21 de Julho de 2012 - 12:13, disse:

Sendo isto uma função recursiva, penso que é desnecessário verificar se o parâmetro passado é ou não um número (e se é ou não positivo).
Este tipo de verificações devem ser feitas antes da parte recursiva (nem que isso implique definir uma função dentro da função factorial).
Imaginem factorial(1000): logo após chamar a função, sabemos que o seu argumento é um número positivo... mas da forma que o código está escrito, também vamos fazer essas verificações para 999, 998, 997, até ao 0, apesar de sabermos que isso é implicitamente verdade.
Podes-me dar um exemplo como ficava o código sff?

#6 pwseo

pwseo

    Unsigned User

  • Moderador
  • PipPipPipPipPipPip
  • 1143 mensagens

Publicado 21 de Julho de 2012 - 13:58

Yana,

Eu simplesmente não faria a verificação dentro da função :)
Mas penso que Python suporta nested functions, o que te permitiria fazer algo tipo isto:
Código (Python):
def factorial(n):
  def f(n):
    if n == 0:
      return 1
    else:
      return n * f(n - 1)

  if isinstance(n, int) and n >= 0:
    return f(n)
  else:
    return None
Atenção, não testei isto :)

#7 Yana

Yana

    null

  • Membro
  • Pip
  • 23 mensagens

Publicado 21 de Julho de 2012 - 14:06

Ver Mensagempwseo, em 21 de Julho de 2012 - 13:58, disse:

Yana,

Eu simplesmente não faria a verificação dentro da função :)
Mas penso que Python suporta nested functions, o que te permitiria fazer algo tipo isto:
Código (Python):
def factorial(n):
  def f(n):
        if n == 0:
          return 1
        else:
          return n * f(n - 1)

  if isinstance(n, int) and n >= 0:
        return f(n)
  else:
        return None
Atenção, não testei isto :)
Ok obrigado, era só para ter uma ideia do código.

#8 msmsms

msmsms

    Boolean User

  • Membro
  • PipPipPip
  • 232 mensagens

Publicado 11 de Agosto de 2012 - 23:12

todos os programas que fizeram a cima estão incorrectos ou incompletos
nenhum funciona no IDE

#9 thoga31

thoga31

    Stack Overflow

  • Moderador
  • PipPipPipPipPipPipPip
  • 7229 mensagens

Publicado 11 de Agosto de 2012 - 23:29

Ver Mensagemmsmsms, em 11 de Agosto de 2012 - 23:12, disse:

todos os programas que fizeram a cima estão incorrectos ou incompletos
nenhum funciona no IDE

Todos funcionaram comigo, nem um falhou. Que erros te dão?
btw, a que te referes com "IDE"? Será IDLE?

Editado por thoga31, 11 de Agosto de 2012 - 23:29.


#10 KTachyon

KTachyon

    Unsigned User

  • Moderador
  • PipPipPipPipPipPip
  • 3390 mensagens

Publicado 11 de Agosto de 2012 - 23:30

Portanto, por um programa não funcionar num IDE significa que está incorrecto ou incompleto? Ou será porque o IDE é uma treta?

#11 thoga31

thoga31

    Stack Overflow

  • Moderador
  • PipPipPipPipPipPipPip
  • 7229 mensagens

Publicado 11 de Agosto de 2012 - 23:41

Aliás, um IDE não interpreta Python. É o interpretador que o faz. Não sei se existem outros interpretadores para além do "original". Nesse caso... moving oooon!

#12 pwseo

pwseo

    Unsigned User

  • Moderador
  • PipPipPipPipPipPip
  • 1143 mensagens

Publicado 12 de Agosto de 2012 - 00:37

msmsms,

Não sei a que te referes. Provavelmente não testaste correctamente.
Aliás, fiz copy-paste da minha sugestão, acrescentei-lhe uma simples instrução print para ver o output, e funciona perfeitamente, com tu mesmo podes comprovar neste link: http://ideone.com/kXN1i

#13 msmsms

msmsms

    Boolean User

  • Membro
  • PipPipPip
  • 232 mensagens

Publicado 15 de Agosto de 2012 - 19:51

Ver Mensagempwseo, em 12 de Agosto de 2012 - 00:37, disse:

msmsms,

Não sei a que te referes. Provavelmente não testaste correctamente.
Aliás, fiz copy-paste da minha sugestão, acrescentei-lhe uma simples instrução print para ver o output, e funciona perfeitamente, com tu mesmo podes comprovar neste link: http://ideone.com/kXN1i


para mim a forma de como fizeram em cima está incompleta e só complica o que é simples
e uma pessoa que não têm capacidade ou qualidade para simplificar não presta para a programação ou para qualquer outra coisa é apenas a minha openião

eu fazia o programa da seguinte forma e bastava!

Código :
# factorial de n
def factorial(n):
 
    f=1
    c=0
 
    while c < n:
                    c = c + 1
                    f = f * c
    return f
if __name__=='__main__':
    n = input ('facturial de:')
    print factorial(n)

Editado por msmsms, 15 de Agosto de 2012 - 19:59.


#14 Yana

Yana

    null

  • Membro
  • Pip
  • 23 mensagens

Publicado 15 de Agosto de 2012 - 20:03

Ver Mensagemmsmsms, em 15 de Agosto de 2012 - 19:51, disse:

para mim a forma de como fizeram em cima está incompleta e só complica o que é simples
e uma pessoa que não têm capacidade ou qualidade para simplificar não presta para a programação ou para qualquer outra coisa é apenas a minha openião

eu fazia o programa da seguinte forma e bastava!

Código :
# factorial de n
def factorial(n):

f=1
c=0

while c < n:
                 c = c + 1
                 f = f * c
return f
if __name__=='__main__':
n = input ('facturial de:')
print factorial(n)
Dude, dominas python? Parabéns :)
Agora eu ainda estou a apender.

Abraço Sentido

#15 thoga31

thoga31

    Stack Overflow

  • Moderador
  • PipPipPipPipPipPipPip
  • 7229 mensagens

Publicado 15 de Agosto de 2012 - 23:28

Vamos lá tornar as coisas interessantes... que tal uma solução de 1 linha, apenas? Ignoro a verificação do input e ignoro o caso do factorial de 0 (zero). :D

Código (Python):
#A seguinte linha vale SÓ para o Python 3!
from functools import reduce

#Colocar os parêntesis no Print para o Python 3!
print reduce(lambda x, y: x * y, [i for i in range(n, 0, -1)])

Editado por thoga31, 15 de Agosto de 2012 - 23:28.


#16 pwseo

pwseo

    Unsigned User

  • Moderador
  • PipPipPipPipPipPip
  • 1143 mensagens

Publicado 16 de Agosto de 2012 - 18:14

msmsms,

Eu até tinha escrito uma resposta grande e decente, mas um dia depois, li este teu juízo de valor absurdo:

Citar

para mim a forma de como fizeram em cima está incompleta e só complica o que é simples
e uma pessoa que não têm capacidade ou qualidade para simplificar não presta para a programação ou para qualquer outra coisa é apenas a minha openião
Quando li isto melhor, apaguei a resposta anterior, e vim escrever esta, que acho mais apropriada.

Espero que a moderação esteja atenta a futuras intervenções tuas onde não lês o que está a ser feito, acusas os outros de incompetência (e na realidade fazes código menos competente) e ainda pensas poder vir falar da aptidão dos outros para programar.

E já agora vou poupar-te o trabalho e dizer-te aquilo que não viste (apesar das tuas skills): as soluções apresentadas fazem tudo o que a tua faz e além disso lidam com input inválido da parte do utilizador (que estava presente no código original do Yana).

Editado por pwseo, 17 de Agosto de 2012 - 14:52.


#17 KTachyon

KTachyon

    Unsigned User

  • Moderador
  • PipPipPipPipPipPip
  • 3390 mensagens

Publicado 17 de Agosto de 2012 - 03:26

Pah, tecnicamente o msmsms ainda está a aprender Python, pelo que acho que a opinião dele não deve influenciar a assim tanto a realidade ;)

Ter que fazer código especial só para "correr" num IDE já é bastante mau, na minha opinião. De facto, tendo em conta que eu prefiro ter total controlo sobre o processo de desenvolvimento, nem sequer costumo ter um IDE entre mim e o meu código.

#18 pwseo

pwseo

    Unsigned User

  • Moderador
  • PipPipPipPipPipPip
  • 1143 mensagens

Publicado 17 de Agosto de 2012 - 15:23

KTachyon disse:

Pah, tecnicamente o msmsms ainda está a aprender Python, pelo que acho que a opinião dele não deve influenciar a assim tanto a realidade ;)
Sim, a realidade não se alterou (de facto, até se riu de algumas coisas), mas a atitude demonstrada (que claramente não foi uma mera partilha de opinião*) é completamente dispensável aqui, como referido pelo criador da thread.

*se por acaso foi apenas uma partilha de opinião, então foi escrita no tom errado (e ninguém é obrigado a "ver o bem" numa resposta mal pensada).

#19 thoga31

thoga31

    Stack Overflow

  • Moderador
  • PipPipPipPipPipPipPip
  • 7229 mensagens

Publicado 17 de Agosto de 2012 - 22:28

O tópico foi trancado por violação das regras do fórum, em especial o ponto 2.2 transcrito em anexo, e pelo facto de esse mesmo post ter resultado numa série de offtopic.

Citar

2. Tópicos e mensagens:
2. Não será tolerada qualquer tipo de falta de respeito para com outro utilizador, o respeito deve ser mutuo e o nosso objectivo é manter a comunidade com um espirito agradável. Mensagens desta natureza poderão ser apagadas ou editadas sem qualquer aviso.
in Regras do Fórum