A Wikipedia diz que Ruby é uma linguagem funcional, mas não estou convencido. Por que ou por que não?
A Wikipedia diz que Ruby é uma linguagem funcional, mas não estou convencido. Por que ou por que não?
Respostas:
Eu definitivamente acho que você pode usar um estilo funcional em Ruby.
Um dos aspectos mais críticos para poder programar em um estilo funcional é se a linguagem suporta funções de ordem superior ... o que Ruby faz.
Dito isso, é fácil programar em Ruby em um estilo não funcional também. Outro aspecto importante do estilo funcional é não ter estado e ter funções matemáticas reais que sempre retornam o mesmo valor para um determinado conjunto de entradas. Isso pode ser feito em Ruby, mas não é imposto na linguagem como algo mais estritamente funcional como Haskell.
Então, sim, ele suporta um estilo funcional, mas também permite que você programe em um estilo não funcional.
Is ruby a functional language?
e em uma resposta direta é um simples não. Ruby é uma linguagem orientada a objetos com alguns recursos funcionais.
Não importa se uma linguagem é ou não funcional. A Programação Funcional é uma tese, melhor explicada por Philip Wadler (The Essence of Functional Programming) e John Hughes (Why Functional Programming Matters).
Uma pergunta significativa é, 'Quão receptiva é Ruby para alcançar a tese de programação funcional?' A resposta é 'muito mal'.
Eu dei uma palestra sobre isso recentemente. Aqui estão os slides.
Ruby oferece suporte a funções de nível superior (consulte Array # map, injetar e selecionar), mas ainda é uma linguagem orientada a objetos imperativa.
Uma das principais características de uma linguagem funcional é evitar o estado mutável. Linguagens funcionais não têm o conceito de variável como você teria em Ruby, C, Java ou qualquer outra linguagem imperativa.
Outra característica fundamental de uma linguagem funcional é que ela se concentra na definição de um programa em termos de "o quê", ao invés de "como". Ao programar em uma linguagem OO, escrevemos classes e métodos para ocultar a implementação (o "como") do "o quê" (o nome da classe / método), mas no final esses métodos ainda são escritos usando uma sequência de instruções. Em uma linguagem funcional, você não especifica uma sequência de execução, mesmo no nível mais baixo.
Eu sugiro que apoiar ou ter a capacidade de programar em uma linguagem em um estilo funcional não significa uma linguagem funcional.
Eu posso até escrever o código Java em um estilo funcional, se eu quiser ferir os meus colegas e eu mesmo alguns meses semanas diante.
Ter uma linguagem funcional não é apenas sobre o que você pode fazer, como funções de ordem superior, funções de primeira classe e currying. É também sobre o que você não pode fazer, como efeitos colaterais em funções puras.
Isso é importante porque é uma grande parte da razão pela qual os programas funcionais são, ou o código funcional em geral é, mais fácil de raciocinar. E quando é mais fácil raciocinar sobre o código, os bugs tornam-se mais superficiais e flutuam até a superfície conceitual onde podem ser corrigidos, o que, por sua vez, resulta em código menos problemático.
Ruby é orientado a objetos em seu núcleo, então, embora tenha um suporte razoavelmente bom para um estilo funcional, ele não é uma linguagem funcional.
Essa é a minha opinião não científica de qualquer maneira.
Editar: Em retrospecto e com consideração pelos bons comentários que recebi a esta resposta até agora, acho que a comparação orientada a objeto versus funcional é uma de maçãs e laranjas.
O verdadeiro diferenciador é ser imparcial na execução, ou não. As linguagens funcionais têm a expressão como sua construção linguística primária e a ordem de execução é freqüentemente indefinida ou definida como preguiçosa. A execução estrita é possível, mas usada apenas quando necessário. Em uma linguagem imparcial, a execução estrita é o padrão e, embora a execução lenta seja possível, costuma ser complicada de fazer e pode ter resultados imprevisíveis em muitos casos extremos.
Agora, essa é minha opinião não científica.
Ruby terá que atender aos seguintes requisitos para ser "VERDADEIRAMENTE" funcional.
Valores imutáveis: uma vez que uma “variável” é definida, ela não pode ser alterada. Em Ruby, isso significa que você efetivamente tem que tratar as variáveis como constantes. O não é totalmente suportado no idioma, você terá que congelar cada variável manualmente.
Sem efeitos colaterais: quando passado um determinado valor, uma função deve sempre retornar o mesmo resultado. Isso anda de mãos dadas com valores imutáveis; uma função nunca pode pegar um valor e alterá-lo, pois isso estaria causando um efeito colateral tangencial ao retorno de um resultado.
Funções de ordem superior: são funções que permitem funções como argumentos ou usam funções como valor de retorno. Esta é, sem dúvida, uma das características mais críticas de qualquer linguagem funcional.
Currying: ativado por funções de ordem superior, currying é transformar uma função que recebe vários argumentos em uma função que leva um argumento. Isso anda de mãos dadas com a aplicação de função parcial, que está transformando uma função com vários argumentos em uma função que recebe menos argumentos do que originalmente.
Recursão: looping chamando uma função de dentro de si mesmo. Quando você não tem acesso a dados mutáveis, a recursão é usada para construir e encadear a construção de dados. Isso ocorre porque o loop não é um conceito funcional, pois requer a passagem de variáveis para armazenar o estado do loop em um determinado momento.
Avaliação preguiçosa ou avaliação adiada: atrasando o processamento de valores até o momento em que é realmente necessário. Se, por exemplo, você tiver algum código que gerou uma lista de números de Fibonacci com a avaliação preguiçosa habilitada, isso não seria realmente processado e calculado até que um dos valores no resultado fosse exigido por outra função, como puts.
Proposta (só uma ideia)
Seria ótimo ter algum tipo de definição para ter uma mode
diretiva para declarar arquivos com paradigma funcional, exemplo
modo 'funcional'
Ruby é uma linguagem multiparadigma que suporta um estilo funcional de programação.
Ruby é uma linguagem orientada a objetos, que pode suportar outros paradigmas (funcional, imperativo, etc). No entanto, como tudo em Ruby é um objeto, é principalmente uma linguagem OO.
exemplo:
"hello" .reverse () = "olleh", cada string é uma instância do objeto string e assim por diante.
Depende da sua definição de “linguagem funcional”. Pessoalmente, acho que o próprio termo é bastante problemático quando usado como um absoluto. Existem mais aspectos em ser uma “linguagem funcional” do que meros recursos de linguagem e a maioria depende de onde você está olhando. Por exemplo, a cultura em torno da língua é muito importante nesse aspecto. Encoraja um estilo funcional? E as bibliotecas disponíveis? Eles encorajam você a usá-los de uma forma funcional?
A maioria das pessoas chamaria Scheme de uma linguagem funcional, por exemplo. Mas e quanto ao Common Lisp? Além do problema de namespace múltiplo / único e eliminação garantida de chamada final (que algumas implementações de CL também suportam, dependendo das configurações do compilador), não há muito que torne Scheme uma linguagem mais adequada para programação funcional do que Common Lisp, e ainda assim, a maioria dos Lispers não chamaria CL de linguagem funcional. Por quê? Porque a cultura que o cerca depende muito dos recursos imperativos do CL (como a macro LOOP, por exemplo, que a maioria dos planejadores provavelmente desaprovaria).
Por outro lado, um programador C pode muito bem considerar CL uma linguagem funcional. Afinal, a maior parte do código escrito em qualquer dialeto Lisp é certamente muito mais funcional em estilo do que seu bloco normal de código C. Da mesma forma, Scheme é uma linguagem imperativa em comparação com Haskell. Portanto, não acho que possa haver uma resposta definitiva sim / não. Chamar uma linguagem de funcional ou não depende muito do seu ponto de vista.
Ruby também não é uma linguagem multiparadigma, eu acho. O multiparadigma tende a ser usado por pessoas que desejam rotular sua linguagem favorita como algo útil em muitas áreas diferentes.
Eu descreveria que Ruby é uma linguagem de script orientada a objetos. Sim, funções são objetos de primeira classe (mais ou menos), mas isso realmente não a torna uma linguagem funcional. IMO, devo acrescentar.
A recursão é comum na programação funcional. Quase todas as linguagens oferecem suporte à recursão, mas os algoritmos recursivos geralmente são ineficazes se não houver otimização de chamada final (TCO).
Linguagens de programação funcional são capazes de otimizar a recursão da cauda e podem executar esse código em espaço constante. Algumas implementações Ruby otimizam a recursão de cauda, as outras não, mas em geral as implementações Ruby não são obrigadas a fazer o TCO. Consulte Ruby executa otimização de chamada de cauda?
Portanto, se você escrever algum estilo funcional Ruby e contar com o TCO de alguma implementação específica, seu código pode ser muito ineficaz em outro interpretador Ruby. Acho que é por isso que Ruby não é uma linguagem funcional (nem Python).
A rigor, não faz sentido descrever uma linguagem como "funcional"; a maioria das linguagens são capazes de programação funcional. Até mesmo C ++ é.
O estilo funcional é mais ou menos um subconjunto de recursos de linguagem imperativos, suportado com açúcar sintático e algumas otimizações do compilador, como imutabilidade e nivelamento de recursão de cauda,
O último, sem dúvida, é um detalhe técnico específico da implementação e não tem nada a ver com a linguagem real. O compilador x64 C # 4.0 faz otimização de recursão de cauda, enquanto o x86 não faz por algum motivo estúpido.
O açúcar sintático geralmente pode ser contornado de uma forma ou de outra, especialmente se a linguagem tiver um pré-compilador programável (isto é, o #define do C).
Pode ser um pouco mais significativo perguntar, "a linguagem __ suporta programação imperativa?", E a resposta, por exemplo, com Lisp, é "não".
Por favor, dê uma olhada no início do livro: "A-Great-Ruby-eBook" . Ele discute o tópico muito específico que você está perguntando. Você pode fazer diferentes tipos de programação em Ruby. Se você deseja programar funcionalmente, pode fazê-lo. Se você quiser programar imperativamente, você pode fazê-lo. É uma questão de definição de quão funcional o Ruby é no final das contas. Por favor, veja a resposta do usuário camflan.