Programação Funcional vs. OOP [fechado]

93

Ouvi muita conversa sobre o uso de linguagens funcionais como Haskell ultimamente. Quais são algumas das grandes diferenças, prós e contras da programação funcional versus programação orientada a objetos?

GSto
fonte
27
Um não rejeita outro.
MBq
11
@mbq eu entendo que eles não são mutuamente exclusivos, mas eu só queria tentar entender melhor a diferença das duas abordagens.
GSto 5/10/10
Ótima pergunta. Eu estive pensando sobre isso também.
JohnFx
A programação funcional e a programação orientada a objetos são ortogonais entre si. Você pode ter os dois no mesmo idioma. Exemplos: Scala, F #, OCaml etc. Talvez você quis dizer funcional versus imperativo, como Jonas sugeriu ?
missingfaktor
4
A resposta real é - não há "versus" entre eles. Confira esta pergunta no StackOverflow .
missingfaktor

Respostas:

67

Eu diria que é mais Programação Funcional vs Programação Imperativa .

A maior diferença é que a programação imperativa é sobre fluxo de controle, enquanto a programação funcional é sobre fluxo de dados . Outra maneira de dizer isso é que a programação funcional usa apenas expressões, enquanto na programação imperativa são usadas expressões e instruções .

Por exemplo, na programação imperativa , variáveis ​​e loops são comuns ao lidar com o estado, enquanto na programação funcional o estado é tratado através da passagem de parâmetros, o que evita efeitos colaterais e atribuições.

Pseudocódigo imperativo para uma função para calcular a soma de uma lista (a soma é mantida em uma variável):

int sumList(List<int> list) {
    int sum = 0;
    for(int n = 0; n < list.size(); n++) {
        sum = sum + list.get(n);
    }

    return sum;
}

Pseudocódigo funcional para a mesma função (a soma é passada como parâmetro):

fun sumList([], sum) = sum
 |  sumList(v::lst, sum) = sumList(lst, v+sum)

Eu recomendo a apresentação Taming Effects with Functional Programming, de Simon Peyton-Jones, para uma boa introdução aos conceitos funcionais.

Jonas
fonte
12
Você deve mencionar que a versão funcional é recursiva de cauda e, portanto, otimizada para evitar estouros de pilha. (Algumas pessoas podem ver a recursão e pensar que a programação funcional é ruim por causa disso)
alternativa
3
+1 para descrever o aspecto mais importante de imperativo versus funcional: fluxo de controle versus fluxo de dados. Uma coisa que devo acrescentar é que o paradigma funcional e o OO não são mutuamente exclusivos; você pode usar o paradigma OO para modelar como o objeto (dados) interage e o paradigma funcional para transformar (manipular) esse objeto.
Lie Ryan
11
Curiosamente, você pode modelar dados como controle e controle como dados, bem como misturar. O FP pode usar setas e funções de primeira ordem para passar o fluxo de controle e manipulá-lo como dados. OOP usa vários padrões de design para usar objetos para alterar o fluxo de controle.
CodexArcanum
Eu acho que também vale a pena notar que a principal diferença não é que você escreve o mesmo programa, mas faz seus loops chamadas de método recursivas de cauda. é muito maior do que
sara
Seu exemplo funcional utiliza a correspondência de padrões de parâmetros. Isso não é exclusivo da programação funcional, os programas funcionais da mesma forma podem usar mônadas e até construções imperativas, sem necessariamente precisar formular todos os algoritmos iterativos como algoritmos recursivos.
Dai
16

A programação funcional é baseada em um modelo declarativo e tem suas raízes no cálculo lambda. Ele oferece muitos conceitos excelentes que podem ser emprestados de linguagens mais importantes, como C ++ e C #.

Alguns exemplos incluem transparência referencial, funções lambda, funções de primeira classe, avaliação preguiçosa e ansiosa e imutabilidade.

Se por nada mais, aprender programação funcional é útil para os conceitos que ela contém. Isso mudará a maneira como você faz a programação e pensa em programação. E eu acho que no futuro a programação funcional será tão importante quanto a programação orientada a objetos.

Para começar, você pode optar por usar uma linguagem funcional pura como Haskell ou uma híbrida como F # .

A maioria das boas universidades cobrirá programação funcional e, se você for à escola, eu sugiro que você faça esse curso.


Quais são algumas das grandes diferenças, prós e contras da programação funcional versus programação orientada a objetos?

A programação orientada a objetos é boa, pois permite modelar seu problema complexo em hierarquias para simplificar o problema. Mas fica muito difícil quando você começa a considerar a programação multithread enquanto usa objetos mutáveis. Nesses casos, você precisa usar muito objetos de sincronização e é quase impossível aperfeiçoar um aplicativo grande.

É aí que entra a programação funcional. Por causa de coisas como a imutabilidade, a programação funcional realmente simplifica os programas multiencadeados. Torna quase trivialmente fácil paralelizar algo quando você sabe que, dada a entrada X para uma função, ela sempre gera Y. Além disso, você sabe que uma variável (ou valor na programação funcional) não pode alterar o uso intermediário de outro encadeamento.

Brian R. Bondy
fonte
2
Para ser claro, Scheme não é de forma alguma uma linguagem funcional pura.
Jonathan Sterling
5
Seu segundo último parágrafo é completamente bs. OO não apresenta problemas no multithreading, a mutabilidade sim. Você parece confundir programação imperativa com programação orientada a objetos. É esse o caso?
Home
5
@missingfaktor: Não, não estou confundindo os conceitos. Um objeto normalmente possui acessadores, modificadores, membros de dados e funções de membro. Sim, nem todos os objetos precisam ter modificadores e você pode implementá-los como imutáveis. Mas se você olhar para qualquer programa OO arbitrário, ele quase certamente terá vários objetos que possuem modificadores e ainda são usados ​​por multiencadeamentos. Ou seja, em um paradigma de POO, é muito raro ter tudo imutável.
Brian R. Bondy
Você deve ler as respostas para esta pergunta: stackoverflow.com/questions/3949618/fp-and-oo-orthogonal/…
missingfaktor
Verifique também a resposta de Frank Shearar aqui: programmers.stackexchange.com/questions/12423/…
missingfaktor
8

(Esta resposta é adaptada de uma resposta para uma pergunta fechada no StackOverflow .)

Uma das grandes diferenças entre programação funcional e programação orientada a objetos é que cada uma é melhor em um tipo diferente de evolução de software:

  • Linguagens orientadas a objeto são bons quando você tem um conjunto fixo de operações sobre as coisas , e como o seu Código evolui, você adiciona principalmente coisas novas. Isso pode ser conseguido adicionando novas classes que implementam métodos existentes, e as classes existentes são deixadas em paz.

  • Linguagens funcionais são boas quando você tem um conjunto fixo de coisas e, à medida que seu código evolui, você adiciona novas operações principalmente às coisas existentes. Isso pode ser conseguido adicionando novas funções que computam com tipos de dados existentes, e as funções existentes são deixadas em paz.

Quando a evolução segue o caminho errado, você tem problemas:

  • Adicionar uma nova operação a um programa orientado a objetos pode exigir a edição de muitas definições de classe para adicionar um novo método.

  • Adicionar um novo tipo de coisa a um programa funcional pode exigir a edição de muitas definições de funções para adicionar um novo caso.

Esse problema é bem conhecido há muitos anos; em 1998, Phil Wadler o chamou de "problema de expressão" . Embora alguns pesquisadores pensem que o problema da expressão pode ser resolvido com recursos de linguagem como mixins, uma solução amplamente aceita ainda não foi atingida.

Norman Ramsey
fonte
Eu amo sua resposta, palavra de sabedoria aqui. Eu o conheci há alguns meses e passei 30 minutos procurando especificamente, pois não os adicionei como favoritos. Apenas a melhor explicação sobre OOP vs FP para aqueles que entendem a vantagem de entender conceitos em vez de técnicas. O artigo sobre o problema da expressão também é fantástico. Muito obrigado por compartilhar sua visão, sua resposta é muito subestimada na minha opinião.
precisa saber é o seguinte
4

Não há real versus. Eles podem ser perfeitamente complementares. Existem idiomas FP, que suportam OOP. Mas as comunidades diferem na maneira como lidam com a modularidade.

Usuários de linguagens FP tendem a obter modularidade através de leis matemáticas. E prefira provas para mostrar conformidade com suas leis.

Em operações imperativas de POO, os usuários tendem a capturar o comportamento do objeto nos casos de teste, que podem ser executados novamente se o objeto tiver sido alterado e alcançar desta maneira a modularidade.

É apenas um aspecto pequeno, mas acho que vale a pena mencionar.

Edgar Klerks
fonte
2

Uma analogia:

Você recebeu uma solicitação de emprego. Você preenche seu nome, informações de contato e histórico de trabalho. Quando terminar, você não terá mais um aplicativo em branco.

Agora imagine agora que, antes de escrever, você o cobre com uma folha clara de celofane. Você escreve seu nome. Você adiciona outra folha de celofane. Você escreve suas informações de contato. Mais celofane. Você escreve seu histórico de trabalho. Quando terminar, você ainda terá o aplicativo em branco intocado. Você também tem três folhas de celofane, cada uma capturando o efeito de uma única mudança discreta.

O primeiro (OOP) abraça a idéia de mudar as coisas no lugar, enquanto o último (FP) evita. Ambos são paradigmas de gerenciamento de estado. Ambos podem, usando estratégias diferentes, capturar o efeito de concluir uma solicitação de emprego. OOP altera o instrumento de partida diretamente, enquanto FP sobrepõe o que veio antes para afetar a aparência da mudança .

Mario T. Lanza
fonte
linda analogia, thx !! você se importaria (se possível) de estender essa analogia com prós e contras nessas duas abordagens.
Rahul Agarwal