Minha resposta será da perspectiva dos negócios do mundo real e dos desafios que toda equipe de desenvolvimento enfrenta. O que vejo nesta pergunta e muitas respostas é realmente sobre o controle de defeitos.
O código pode estar livre de erros. Pegue qualquer um dos exemplos de código "Hello World" para qualquer linguagem de programação e execute-o na plataforma pretendida, que funcionará de forma consistente e produzirá os resultados desejados. Termina qualquer teoria sobre a impossibilidade de código estar livre de erros.
Os erros em potencial aparecem à medida que a lógica se torna mais complexa. O exemplo simples do Hello World não tem lógica e faz a mesma coisa estática a cada vez. Assim que você adiciona um comportamento dinâmico controlado por lógica, é isso que introduz a complexidade que leva aos erros. A própria lógica pode ser falha ou os dados que são inseridos na lógica podem variar de uma maneira que a lógica não lida.
Um aplicativo moderno também depende de bibliotecas de tempo de execução, CLR, middleware, banco de dados, etc. camadas que, ao mesmo tempo em que economizam tempo de desenvolvimento, também são camadas em que os erros nessas camadas podem existir e passar despercebidos pelo desenvolvimento e testes UAT e para produção.
Por fim, a cadeia de aplicativos / sistemas em que o aplicativo consome dados que alimentam sua lógica são todas fontes de possíveis bugs, dentro da lógica ou no software que empilha as lógicas sobre os sistemas de upstream que consome dados.
Os desenvolvedores não estão no controle de 100% de cada peça móvel que suporta a lógica de sua aplicação. Na verdade, não temos controle de muito. É por isso que o teste de unidade é importante, e o gerenciamento de configurações e alterações são processos importantes que não devemos ignorar ou ser preguiçosos / desleixados.
Além disso, acordos documentados entre o aplicativo que consomem dados de uma fonte fora do seu controle, que define o formato e as especificações específicos para os dados transferidos, bem como quaisquer limites ou restrições que seu sistema assume que o sistema de origem é responsável por garantir que a saída esteja dentro esses limites.
No aplicativo de engenharia de software do mundo real, você não será capaz de fazê-lo voar, explicando aos negócios por que, teoricamente, os aplicativos não podem estar livres de erros. Discussões dessa natureza entre tecnologia e negócios nunca acontecerão, exceto após um mau funcionamento tecnológico que tenha impactado a capacidade da empresa de ganhar dinheiro, evitar perder dinheiro e / ou manter as pessoas vivas. A resposta para "como isso pode acontecer" não pode ser "deixe-me explicar essa teoria para você entender".
Em termos de cálculos maciços que teoricamente poderiam levar uma eternidade para realizar o cálculo e obter um resultado, um aplicativo que não pode terminar e retornar com um resultado - isso é um bug. Se a natureza da computação é tal que consome muito tempo e consome muita computação, você atende a essa solicitação e fornece feedback ao usuário sobre como / quando ele pode recuperar o resultado e inicia os encadeamentos paralelos para agitá-lo. Se isso precisa acontecer mais rapidamente do que pode ser feito em um servidor e é importante para os negócios, você o expande em todos os sistemas necessários. É por isso que a nuvem é muito atraente e a capacidade de ativar nós para trabalhar e diminuí-los quando terminar.
Se existe a possibilidade de obter uma solicitação de que nenhuma quantidade de energia de computação pode ser concluída, ela não deve ficar lá correndo infinitamente, com um processo de negócios aguardando a resposta para o que a empresa considera um problema finito.
print "Hello, World!"
... você pode ser um pouco mais claro?