O sistema de tipos de Haskell é um obstáculo para entender a programação funcional? [fechadas]

33

Estou estudando Haskell com o objetivo de entender a programação funcional, com a expectativa de aplicar a percepção que obtiver em outras linguagens (principalmente Groovy, Python, JavaScript).

Escolhi Haskell porque tive a impressão de que é muito puramente funcional e não permitiria nenhuma confiança no estado.

Não escolhi aprender Haskell porque estava interessado em navegar em um sistema do tipo extremamente rígido.

Minha pergunta é a seguinte: Um sistema de tipo forte é um subproduto necessário de uma linguagem funcional extremamente pura ou é uma opção de design não relacionada específica da Haskell?

Eric Wilson
fonte
6
Se você não deseja digitar nada explicitamente, não precisa digitar nada explicitamente. Haskell pode inferir tipos por si só. E não é como se você tivesse uma única variável potencialmente armazenando dois tipos incompatíveis.
Anon.
4
@ Anon sim, mas suas listas devem ser homogêneas. Confie em mim, esse tipo de coisa pode atrapalhar, mesmo com inferência de tipo.
Eric Wilson
13
@FarmBoy e o que há de errado com o uso do Maybe? Java realmente faz você usar Talvez em todas as classes, o que é estranho.
alternativa
3
E se você realmente deseja usar uma lista heterogênea, é claro que pode usar tipos de dados algébricos.
alternativa
1
@mathepic Neste ponto, realmente perdemos a noção da minha pergunta original, que era uma pergunta perfeitamente válida.
Eric Wilson

Respostas:

40

Acredito que entender o sistema de tipos de Haskell é um amplificador para entender a programação funcional.

A questão da programação puramente funcional é que, na ausência de efeitos colaterais, que permitem fazer todo tipo de coisa implicitamente, a programação puramente funcional torna a estrutura dos seus programas muito mais explícita.

Haskell impede que você jogue as coisas debaixo do tapete, obriga a lidar com a estrutura do seu programa explicitamente e ensina uma linguagem para descrever essas estruturas: a linguagem dos tipos. Compreender tipos, tipos particularmente ricos como o Haskell, fará de você um programador melhor em qualquer idioma.

Se Haskell não fosse fortemente tipado, conceitos como mônadas, functores aplicativos e afins nunca seriam aplicados à programação.

Waquo
fonte
2
Essa é uma boa resposta, e minha adição é que, embora o sistema de tipos possa parecer incomum a princípio, mais tarde, quando você começar a aprender os conceitos mais avançados, verá que há certas coisas que só podem ser feitas devido à adesão a esse tipo (adicione STM e Data Parallel à lista acima). Coisas que não seriam iniciantes em outros sistemas de tipos se encaixam naturalmente com o sistema Haskell. Meu conselho: fique com ele por um tempo, deixe-o afundar com o tempo (não é uma linguagem "empinado").
anon
2
Eu sei que esta é uma resposta super antiga, mas eu realmente discordo. Penso que, por mais explícito que possa haver na linguagem, o sistema de tipos, especialmente com mônadas como State e Parsec, varre uma tonelada de coisas para debaixo do tapete. Na verdade, isso está interferindo bastante na minha capacidade de aprender as bibliotecas da linguagem.
Savanni D'Gerinel
4
@ SavanniD'Gerinel: Eu acho que nesta resposta "enfiar as coisas debaixo do tapete" não significa adicionar funcionalidades implícitas (o que Haskell faz de maneira controlada, por exemplo, através de mônadas, e que ajuda a reduzir o clichê), mas sim permitir algum código faça algo que não se espera que faça. Por exemplo: uma função pura em Haskell nunca terá efeitos colaterais. Período. Em muitos outros idiomas, você pode prometer isso na documentação de uma função, mas nada no seu idioma o impedirá de colocar alguns efeitos colaterais em algum lugar do código.
Giorgio
33

A linguagem funcional mais dinamicamente digitada é Scheme. Dito isto, o sistema de tipos de Haskell é um indicador de sua pureza. É uma questão de "como se mede a pureza?". O sistema de tipos de Haskell permite isolar facilmente ações impuras IO. Para fazer isso, você precisa de um sistema de tipo estático.

Mas digamos que o sistema de tipos de Haskell não tenha nada a ver com programação funcional. Ainda seria a altura da arrogância afirmar que o sistema de tipos não o ajudaria nesse empreendimento educacional. O sistema de tipos de Haskell é rico e complexo, e ainda mais interessante quando comparado aos sistemas de tipos de C ++ e OCaml.

Isso é um obstáculo? Não, acho que é um trunfo. Tente considerar como lidar com a preguiça de Haskell sem, IOpor exemplo.

Logan Capaldo
fonte
8
O sistema de tipos de Haskell +1 pode ser seu amigo assim que você se acostumar.
Larry Coleman
"Para fazer isso, você precisa de um sistema de tipo estático". Sério?
26512 Jon Harrop
1
"ainda mais interessante quando comparado aos sistemas de tipos de C ++ e OCaml". Você estudou os módulos de primeira ordem de primeira classe do OCaml e o sistema de objetos inferidos com estrutura estrutural e variantes polimórficas?
26512 Jon Jonop
2
@ JonHarrop ou um sistema de efeitos ou alguma maneira de medir / avaliar a pureza. Sim, é por isso que é interessante compará-los. Diferentes escolhas fazem para diferentes idiomas.
Logan Capaldo
20

O Clojure é do tipo dinâmico e quase tão puro quanto o Haskell; portanto, há um bom argumento de que o sistema de tipos do Haskell era mais uma opção de design do que um requisito absoluto. Ambos definitivamente têm seus pontos fortes, então você pode considerar o Clojure se realmente não gosta da rigidez de Haskell (mas veja abaixo).

Quando comecei a usar o Haskell, considerei o sistema de tipos irritante e só o tolerava devido à inferência de tipos. Logo descobri que muitos dos erros de tipo que o compilador se queixava de coisas que não teriam funcionado de qualquer maneira, mesmo que o compilador me tivesse permitido fazê-lo (por exemplo, acidentalmente usando o mapa em vez do concatMap). Descobri então que os programas que passaram na verificação de tipo estavam geralmente corretos, ou pelo menos perto de corrigir. Eu até tive uma fase preguiçosa em que refatorei alterando um tipo de função e deixando o compilador me dizer o que mais precisava ser mudado. Finalmente, percebi que o sistema de tipos de Haskell era realmente muito expressivo e comecei a projetar meus programas em torno de tipos. Esse é o Santo Graal de Haskell.

Larry Coleman
fonte
Outra coisa a ser observada: aprendi programação funcional usando Scheme e Haskell mais ou menos ao mesmo tempo (o primeiro para uma classe e o segundo por diversão). Eu descobri que entender a recursão era muito mais fácil com a correspondência de padrões de Haskell do que com ifs e conds em Scheme, que eu imagino que também seja transferido para Clojure.
Tikhon Jelvis
@ Larry Coleman: +1 por descrever com precisão minha própria experiência com sistemas de tipos: primeiro C ++, depois Ocaml e agora minha própria linguagem Felix. Sim, eu ainda refatoro perseguindo erros do compilador.
Yttrill
8

O sistema de tipos de Haskell é a chave para sua capacidade de isolar efeitos do código puro. A menos que você possa isolar efeitos de outra maneira ou remover completamente os efeitos, um sistema de tipo estático forte é um requisito para a programação funcional pura.

Haskell é um exemplo muito bom de uma linguagem com um sistema de tipos estático forte. Se você deseja uma educação ampla e abrangente em ciência da computação e design de linguagem de programação em particular, Haskell seria uma excelente escolha como uma das línguas que você deveria aprender.

O sistema de tipos não deve ser um grande obstáculo. As pessoas que programam tendem a, mesmo quando usam linguagens dinâmicas, seguir convenções de digitação que podem ser codificadas usando o sistema de tipos de Haskell. Haskell também apresenta inferência de tipo que alivia a verbosidade quando comparado a linguagens como C ++ e Java. Quando você recebe uma mensagem de erro, o compilador está apenas dizendo em tempo de compilação o que uma linguagem com tipos dinâmicos diria em tempo de execução.

O oposto de um sistema de tipo dinâmico é um sistema de tipo estático, não um sistema de tipo forte. Um sistema de tipo forte é o oposto de um sistema de tipo fraco.

dan_waterworth
fonte
1
Por exemplo, C é estaticamente, mas com fraca digitação. Você tem tipos, mas é fácil subverter completamente o sistema de tipos, brincar com as representações específicas da máquina subjacentes, etc. Muitas linguagens dinamicamente digitadas OTOH são fortemente tipadas - poucas conversões implícitas, poucas maneiras (se houver) de subverter o sistema de tipos.
Steve314
4

Ele informa imediatamente quando você comete erros estúpidos. Isso é útil. Eu tenho trabalhado em Racket (Scheme) neste último período e houve várias vezes em que passei um s-exp não analisado em que esperava um ast analisado para alguma função no meu intérprete, e ele só apareceu no meu suíte de teste de tamanho médio. Se eu tivesse alguma digitação estática, isso teria sido trazido à minha atenção imediatamente.

Obviamente, os erros lógicos não podem realmente ser detectados pelo sistema de tipos, mas o número de maneiras pelas quais você pode errar é bastante reduzido.

Além disso, a inferência de tipo permite ignorar o sistema de tipos, se desejar. Ainda está lá, mas não requer informações ativas de sua parte. Ainda é útil entender os tipos de suas funções, mas o código correto funcionará bem.

A pureza de Haskell é codificada em seu sistema de tipos. A mônada de E / S é uma construção no nível de tipo que impede que o código impuro vaze para funções puras, portanto a pureza é garantida pelo sistema de tipos.

Theo Belaire
fonte
8
Se você acha que pode ignorar o sistema de tipos de Haskell, acho que não codificou muito Haskell.
Eric Wilson
Não ignore tanto quanto ignore, mas digite a função, carregue-a no GHCi e continue: t. Mas você ainda precisará polvilhar algumas funções internas ou outras, algumas vezes.
Theo Belaire
1
Tyr, mesmo com inferência de tipo, 90% do uso e codificação de funções Haskell está fazendo com que as coisas malditas se misturem, o que requer uma compreensão de seu sistema de tipos e mensagens de erro de verificação de tipo arcana. Mesmo ": t" não é uma solução mágica, apenas o primeiro passo para entender como fazer o programa compilar.
Andres F.
Bem, algumas partes estão confusas, eu concordo. Eu realmente acho que o material numérico no prelúdio pode ser limpo e consertado, porque, como está, é uma bagunça terrível. Mas a maioria dos principais aspectos funcionais é bastante limpa. map, filter, foldr / le outras funções funcionais divertidas funcionam muito bem.
Theo Belaire
2

Ser uma linguagem "funcional" significa (além de outras coisas) que funções são objetos de primeira classe na linguagem.

Ser uma linguagem "pura" significa que funções são funções matemáticas (ao contrário de procedimentos) - com a mesma entrada, elas sempre produzem a mesma saída.

Uma "linguagem funcional pura" é aquela em que ambos os itens acima se aplicam. Não tenho conhecimento de um "pura- ly linguagem funcional".

Um sistema de tipo forte é uma maneira limpa de ter uma linguagem pura e prática. Os tipos ajudam o compilador a descobrir otimizações, além de garantir a correção. (Mas essa não é a única maneira - o clojure é puro, mas não possui um sistema de tipos tão forte quanto Haskell.)

Se o sistema de tipos o estiver incomodando, sugiro que tente uma linguagem mais dinâmica, como Scheme, ou use o sistema de inferência de tipos de Haskell.

pyNem
fonte
0

Sim, o sistema de tipos é um ativo incrível. Seria muito difícil até descrever como as mônadas funcionam ou como alguns combinadores operam sem o sistema de tipos. Considere quantos tutoriais sobre Haskell primeiro pedem que você considere o tipo de função em questão com a: t no REPL. Isso simplesmente não está disponível para você em um idioma digitado dinamicamente. Claro, toda a complexidade do sistema de tipos ainda está lá. Uma mônada ainda é uma mônada. Mas o idioma decidiu lavar as mãos do assunto e não fornecer nenhuma ajuda. Você está por sua conta, amigo. Eu não estou batendo em idiomas dinamicamente digitados. Eu os amo ternamente. O esquema é uma ferramenta elétrica por excelência. Mas você notará que, quando falamos sobre mônadas em linguagens dinâmicas, geralmente inventamos uma notaçãopara descrever o tipo de procedimentos. Um programador funcional irá lutar com os tipos de uma maneira ou de outra. O verificador de tipos de Haskell apenas fornece boas ferramentas para você aprender como fazer isso.

Ara Vartanian
fonte