Os modelos C ++ são notórios por gerar mensagens de erro longas e ilegíveis. Eu tenho uma idéia geral de por que as mensagens de erro do modelo em C ++ são tão ruins. Essencialmente, o problema é que o erro não é acionado até que o compilador encontre uma sintaxe que não é suportada por um determinado tipo de modelo. Por exemplo:
template <class T>
void dosomething(T& x) { x += 5; }
Se T
não suportar o +=
operador, o compilador gerará uma mensagem de erro. E se isso acontecer dentro de uma biblioteca em algum lugar, a mensagem de erro pode ter milhares de linhas.
Mas os modelos C ++ são essencialmente apenas um mecanismo para digitação de patos em tempo de compilação. Um erro de modelo C ++ é conceitualmente muito semelhante a um erro de tipo de tempo de execução que pode ocorrer em uma linguagem dinâmica como Python. Por exemplo, considere o seguinte código Python:
def dosomething(x):
x.foo()
Aqui, se x
não houver um foo()
método, o interpretador Python lança uma exceção e exibe um rastreamento de pilha junto com uma mensagem de erro bastante clara indicando o problema. Mesmo que o erro não seja acionado até que o intérprete esteja profundamente dentro de alguma função da biblioteca, a mensagem de erro de tempo de execução ainda não será tão ruim quanto o vômito ilegível emitido por um compilador C ++ típico. Então, por que um compilador C ++ não pode ser mais claro sobre o que deu errado? Por que algumas mensagens de erro do modelo C ++ literalmente fazem com que a janela do meu console role por mais de 5 segundos?
fonte
clang++
wink wink).Respostas:
As mensagens de erro do modelo podem ser notórias, mas nem sempre são longas e ilegíveis. Nesse caso, a mensagem de erro inteira (do gcc) é:
Como no exemplo do Python, você obtém um "rastreamento de pilha" dos pontos de instanciação do modelo e uma clara mensagem de erro indicando o problema.
Às vezes, as mensagens de erro relacionadas ao modelo podem demorar muito mais, por vários motivos:
A principal diferença do Python é o sistema de tipo estático, levando à necessidade de incluir os nomes de tipo (às vezes longos) na mensagem de erro. Sem eles, às vezes seria muito difícil diagnosticar por que a resolução da sobrecarga falhou. Com eles, seu desafio não é mais adivinhar onde está o problema, mas decifrar os hieróglifos que lhe dizem onde está.
Além disso, a verificação no tempo de execução significa que o programa será interrompido no primeiro erro encontrado, exibindo apenas uma única mensagem. Um compilador pode exibir todos os erros que encontrar, até que desista; pelo menos em C ++, ele não deve parar no primeiro erro no arquivo, pois isso pode ser uma consequência de um erro posterior.
fonte
Algumas das razões óbvias incluem:
Isso está longe de ser exaustivo, mas você entende a ideia geral. Mesmo que não seja fácil, a maior parte pode ser curada. Por anos, venho dizendo às pessoas para obter uma cópia do Comeau C ++ para uso regular; Provavelmente salvei o suficiente de uma mensagem de erro uma vez para pagar pelo compilador. Agora Clang está chegando ao mesmo ponto (e é ainda mais barato).
Termino com uma observação geral que soa como uma piada, mas realmente não é. Na maioria das vezes, o trabalho real de um compilador honestamente é transformar código fonte em mensagens de erro. Já é tempo de os fornecedores se concentrarem em fazer esse trabalho um pouco melhor - embora eu admita abertamente que, quando escrevi compiladores, tive uma forte tendência a tratá-lo como secundário (na melhor das hipóteses) e, em alguns casos, quase o ignorei. completamente.
fonte
A resposta é simples, porque o Python foi projetado para funcionar dessa maneira, enquanto muitas das coisas associadas aos modelos surgiram por acidente. Ele nunca teve a intenção de se tornar um sistema completo de Turing, por exemplo. E se você não pode planejar e argumentar deliberadamente sobre o que acontece quando o sistema funciona , por que alguém deveria esperar um planejamento cuidadoso e cuidadoso sobre o que acontece quando algo dá errado?
Além disso, como você apontou, o interpretador Python pode facilitar muito a exibição de um rastreamento de pilha, porque está interpretando o código Python. Se um compilador C ++ detectar um erro de modelo e fornecer um rastreamento de pilha, isso seria tão inútil quanto "vômito de modelo", não seria?
fonte