Lucchesi
topo

A polêmica carta de Dijkstra sobre linguagens de programação para iniciantes

Se você é da computação, você já deve ter ouvido falar em Edsger Dijkstra. O que talvez você não tenha ouvido é a opinião dele sobre o uso de programação imperativa e linguagens como Java ou C++ para ensinar programação para iniciantes — uma prática muito comum, hoje em dia, nos currículos de Ciência da Computação no Brasil e no mundo.

Dijkstra descreveu o que ele pensa sobre o assunto em uma carta enviada ao Conselho Orçamentário da Universidade do Texas (UT Austin) em abril de 2001. Neste artigo, eu traduzi a carta original para português:

Aos membros do Conselho Orçamentário

Eu escrevo a vocês por causa de um rumor de esforços para substituir no curso introdutório de programação do nosso currículo de graduação a linguagem de programação funcional Haskell pela linguagem imperativa Java, e porque eu acredito que neste caso o Conselho Orçamentário tem que assumir a responsabilidade para que a decisão não seja tomada no nível errado.

Vejam, este não é um assunto sem importância. Colegas de outros estados muitas vezes se perguntam (ainda!) como eu consigo sobreviver em um lugar como Austin, Texas, automaticamente assumindo que o conservadorismo sólido do Texas implica uma mediocridade igualmente sólida. Minha resposta habitual é algo como: “Não se preocupem. O Departamento de Ciência da Computação é um lugar bastante esclarecido, por exemplo, para introdução à programação nós apresentamos Haskell aos nossos calouros”; eles reagem, primeiro, quase com descrença, e então com inveja — geralmente porque o currículo de graduação deles ainda não se recuperou da transição de Pascal para algo como C++ ou Java.

Uma razão muito prática para preferir programação funcional em um curso para iniciantes é que a maioria dos estudantes já tem uma certa familiaridade com programação imperativa. Colocá-los de frente com a novidade da programação funcional imediatamente faz com que eles levem para casa a mensagem de que existe mais sobre programação do que eles imaginavam. E rapidamente eles irão observar que a programação funcional admite elegantemente soluções que são muito difíceis (ou impossíveis) de formular com o veículo de programação de seus tempos de colégio.

Uma razão fundamental para a preferência é que programas funcionais são muito mais facilmente apreciados como objetos matemáticos do que os imperativos, de modo que você pode ensinar o que um raciocínio rigoroso sobre programas significa. A vantagem adicional de programação funcional com “avaliação preguiçosa” é que ela provê um ambiente que desencoraja o raciocínio operacional1.

Finalmente, na comparação específica de Haskell contra Java, Haskell, embora não seja perfeita, é de uma qualidade que é várias ordens de magnitude superior à Java, que é uma bagunça (e precisou de uma extensa campanha publicitária e vendas agressivas para sua aceitação comercial). Já é ruim o suficiente que, no geral, a indústria aceite projetos de péssima qualidade como padrões “de facto”. Pessoalmente, acredito que a Universidade deva manter vivas as alternativas mais saudáveis.

Não é só o violino que molda o violinista, somos todos moldados pelas ferramentas que treinamos para usar, e nesse aspecto, as linguagens de programação têm uma influência tortuosa: elas moldam nossos hábitos de pensamento. Esta circunstância torna a escolha da primeira linguagem de programação tão importante. Qualquer um gostaria de usar o curso de programação introdutória como um meio de criar uma cultura que possa servir de base para um currículo de Ciência da Computação, ao invés de ser forçado a começar com muitos “desaprendizados” (se é que isso é possível, pois o que se torna nosso passado, permanece para sempre assim). Esta escolha implica uma grave responsabilidade para com nossos estudantes de graduação, e é por isso que não pode ser deixada a cargo de um presidente aleatório de alguma coisa, mas deve ser tomada pelo Conselho Orçamentário. Isso não é algo que pode ser deixado para funcionários públicos ou políticos; aqui são necessários estadistas.

Edsger Dijkstra
Austin, 12 de abril de 2001

  1. Raciocínio operacional significa raciocinar sobre os programas pensando em como a máquina que executa o programa irá operar: qual efeito cada instrução terá no estado da máquina, o que o programa fará em seguida, etc — simulando o processador (ou um interpretador abstrato) na sua cabeça. Fonte: Operational Reasoning.