Qual idioma, na sua opinião, permite que o programador médio produza recursos com a menor quantidade de bugs difíceis de encontrar? Naturalmente, essa é uma pergunta muito ampla, e estou interessado em respostas e conhecimentos muito amplos e gerais.
Pessoalmente, acho que passo muito pouco tempo procurando bugs estranhos nos programas Java e C #, enquanto o código C ++ tem seu conjunto distinto de bugs recorrentes, e o Python / similar tem seu próprio conjunto de bugs comuns e tolos que seriam detectados pelo compilador em outros idiomas.
Também acho difícil considerar linguagens funcionais nesse sentido, porque nunca vi um programa grande e complexo escrito em código totalmente funcional. Sua entrada, por favor.
Editar: Clarificação completamente arbitrária do bug difícil de encontrar: leva mais de 15 minutos para reproduzir ou mais de 1 hora para encontrar a causa e a correção.
Perdoe-me se for uma duplicata, mas não encontrei nada sobre esse tópico específico.
fonte
Respostas:
Quanto mais poderoso o sistema de tipos de linguagem, mais erros serão detectados no momento da compilação.
A figura a seguir compara algumas das linguagens de programação conhecidas em termos de potência, simplicidade e segurança de seus sistemas de tipos. [ Fonte ]
* Factoring na capacidade de usar construções inseguras.
fonte
(let ((itbe '())) ... )
...Na minha opinião, Haskell ajuda a evitar algumas fontes comuns de erros:
null
não faz parte das definições de tipo de valor: com isso, você evita o erro de um bilhão de dólaresfonte
null
, existeundefined
, o que é um membro de cada tipo.)Tradicionalmente, os bugs mais difíceis de encontrar são as condições de corrida em aplicativos multithread como estão.
Portanto, você precisa de linguagens que gerenciem o paralelismo para você o máximo e sem intrusões possível. Estes ainda não são comuns. Java faz alguns, mas deixa você com a parte mais difícil.
No meu entender, você precisa de uma linguagem funcional, já que o "sem efeitos colaterais" é o que, em primeiro lugar, faz com que os dois pontos de bala desapareçam. Vi que o trabalho está em andamento para tornar o Haskell de maneira transparente uma linguagem multiencadeada eficiente, e acredito que o Fortress foi projetado desde o início para ser uma linguagem paralela eficiente.
Editar: No Java,
Executors
lida com ainda mais partes difíceis. Você precisa tornar as tarefas individuais em conformidade com aCallable
interface.fonte
O Ada foi projetado para que o máximo possível seja capturado no tempo de compilação, em vez do tempo de execução. O que isso significa é que geralmente leva cerca de 10x mais tempo para que um programa no Ada seja compilado do que o equivalente em Java diria, mas quando ele é compilado, você pode ficar muito mais confiante de que classes inteiras de bugs não se manifestam quando o programa é executado. corre.
fonte
Primeiro, uma definição: um bug difícil de encontrar, pelo que entendi, é um bug que pode ser reproduzido, mas a causa é difícil de encontrar.
Provavelmente, o aspecto mais importante é o que eu chamaria de estreiteza , ou seja, até que ponto um bug pode escapar, qual o tamanho do escopo que um bug pode potencialmente influenciar. Em linguagens como C, um bug, por exemplo, um índice de matriz negativo ou ponteiro não inicializado, pode afetar literalmente tudo em qualquer lugar do programa, portanto, na pior das hipóteses, você deve verificar tudo em todos os lugares para encontrar a fonte do seu problema.
Bons idiomas nesse sentido oferecem suporte a modificadores de acesso e os impõem de uma maneira que dificulta ou impossibilita ignorá-los. Boas linguagens incentivam você a limitar o escopo de suas variáveis, em vez de facilitar a criação de variáveis globais (por exemplo, "tudo o que não foi declarado explicitamente é uma variável global com um tipo e valor padrão").
O segundo aspecto importante é a simultaneidade . As condições da corrida são geralmente difíceis de reproduzir e, portanto, difíceis de encontrar. Boas linguagens oferecem mecanismos de sincronização fáceis de usar, e suas bibliotecas padrão são seguras contra threads sempre que necessário.
Isso já completa minha lista; outras coisas, como digitação forte, ajudam a detectar bugs em tempo de compilação, mas provavelmente não será difícil encontrá-los mais tarde.
Considerando tudo isso, eu diria que Java e C #, e muitas outras linguagens no mundo da JVM e .net, são adequados para evitar erros difíceis de encontrar.
fonte
Como o Excel é o DSL mais usado, irei ao Excel. (exceto VBA, é claro)
Ele se encaixa na conta:
fonte
123
ouABC
) ou como função (=SUM(A2:A5)
). O Excel avalia todas as variáveis, descobrindo em que ordem resolver as dependências, etc. Certamente não são apenas dados.Essa é uma pergunta difícil, porque a maioria dos erros não é culpa da própria linguagem - eles são cometidos por desenvolvedores cometendo erros na maneira como usam a linguagem.
Acredito que existem vários aspectos dos recursos de linguagem que afetam a probabilidade de erros:
Interatividade - linguagens dinâmicas com REPLs incentivam a interação / experimentação com programas em execução e ciclos de código / teste muito menores. Se você acredita que a iteração é uma boa maneira de descobrir soluções simples e limpas e detectar / eliminar bugs, isso tenderia a favorecer linguagens interativas.
Expressividade - se o código for mais curto e tiver menos complexidade padrão / incidental, será mais fácil ver bugs / erros lógicos.
Segurança do tipo - quanto mais a verificação do tempo de compilação, mais erros serão detectados pelo compilador, portanto, em geral, a segurança do tipo é uma coisa boa. No entanto, esses erros normalmente não são difíceis de encontrar - mesmo em uma linguagem totalmente dinâmica, o tipo errado em uma estrutura de dados geralmente causa um erro de execução muito óbvio, e o TDD quase sempre captura esse tipo de erro.
Imutabilidade - muitos erros graves são causados por interações complexas de estado mutável. Idiomas que enfatizam a imutabilidade (Haskell, Clojure, Erlang) têm uma enorme vantagem ao evitar a mutabilidade
Programação funcional - as abordagens funcionais para escrever código tendem a ser mais "comprovadamente corretas" do que o código orientado a objetos, com sequências complexas de efeitos / interações. Minha experiência é que o FP ajuda a evitar erros complicados - acredito que há alguma pesquisa acadêmica em algum lugar que atualmente não consigo encontrar que apóie isso.
Suporte à simultaneidade - problemas de simultaneidade são particularmente difíceis de detectar e depurar, e é por isso que isso é tão importante. Qualquer coisa que exija bloqueio manual está fadada ao fracasso (e isso inclui praticamente todas as abordagens orientadas a objetos da concorrência). O melhor idioma que conheço a esse respeito é o Clojure - ele possui uma abordagem única para gerenciar a simultaneidade que combina memória transacional de software com estruturas de dados imutáveis para obter uma nova estrutura de simultaneidade, confiável e componível. Consulte http://www.infoq.com/presentations/Value-Identity-State-Rich-Hickey para obter mais informações
fonte
Quanto menos poderosa é a linguagem, menos opções ela oferece para atirar no próprio pé.
Linguagens de alto nível como Java e C # produzirão menos erros do que linguagens de baixo nível como C ++.
Dito isto, acredito que o Java é mais seguro que o C #. O Java é artificialmente limitado para que um programador comum, sem conhecimento avançado, possa dominá-lo e produzir programas estáveis.
fonte
Na minha opinião, Delphi. Baseada no Pascal, a linguagem é simples e intuitiva o suficiente para que o programador médio (ou mesmo os codificadores inexperientes) possam entender facilmente, e seu rico suporte de ferramentas e bibliotecas facilita a localização de muitos bugs.
if (alert = RED) {LaunchNukes;}
, não será compilado, por exemplo.)fonte
var I: Integer; Pointer(I)^ := $00;
Uma coisa a levar em consideração é a mudança de direção.
Nos últimos cinco anos, desenvolvi principalmente aplicativos da Web em java (JSF, Seam, etc.). Recentemente, consegui um novo emprego e estamos usando o Perl (com Catalyst e Moose).
Sou muito mais produtivo em Perl do que em Java.
Não é necessário compilar e implantar (quente), é um dos motivos. Também acho que escrever casos de uso é mais fácil, pois isso pode ser feito de maneira mais iterativa. E as estruturas em Java parecem ser desnecessárias e complexas, pelo menos para os projetos nos quais estive envolvido.
Eu acho que o número de bugs no meu código Perl é mais ou menos o mesmo que o número de bugs no meu código Java, pode até ser maior. Mas acho mais fácil e rápido encontrar e corrigir esses erros.
fonte
Talvez o levantamento do número de ferramentas disponíveis para análise de código estático e dinâmico para cada linguagem de programação possa dar uma idéia. Quanto mais ferramentas para um idioma, é mais provável que o idioma seja muito popular entre os usuários ou muito popular na geração de bugs difíceis de encontrar. Mas não consigo convencer o Google a fazer nenhum estudo sobre esse assunto. Também deve ser observado que alguns idiomas, como C, podem ser usados para solucionar os bugs de hardware subjacentes, bem como para solucionar o desgaste do hardware à medida que envelhece.
fonte
Em vez de falar sobre idiomas, que tal falar sobre recursos de idioma
fonte