Vedo solo risposte su di noi essere umani e inclini a sbagliare, il che è molto vero ... ma vedo la tua domanda da un altro punto di vista.
Penso che tu possa scrivere programmi senza bug, ma quelli in genere sono programmi che hai già scritto 10 o 12 volte. La tredicesima volta che scrivi lo stesso programma da zero, sai già come farlo: conosci il problema, conosci le tecniche, conosci le librerie, il linguaggio ... lo vedi nella tua mente. Tutti i modelli sono lì, a tutti i livelli.
Questo mi succede con programmi molto semplici perché insegno programmazione. Sono semplici per me, ma difficili per gli studenti. E non sto parlando di soluzioni a problemi che ho fatto molte, molte volte alla lavagna. Certo che conosco quelli. Intendo programmi a circa 300 righe che risolvono qualcosa usando concetti che conosco molto bene (i concetti a cui insegno). Scrivo questi programmi senza pianificazione e funzionano e sento di conoscere tutti i dettagli, non ho bisogno del TDD. Ottengo un paio o tre errori di compilazione (principalmente errori di battitura e altre cose del genere) e basta. Posso farlo per piccoli programmi e credo anche che alcune persone possano farlo per programmi più complicati. Penso che persone come Linus Torvalds o Daniel J. Bernstein abbiano una tale chiarezza mentale, sono le più vicine che puoi ottenere a un programmatore privo di bug. Se tucapire le cose in profondità penso che tu possa farlo. Posso farlo solo per programmi semplici, come ho detto.
La mia convinzione è che se provi sempre a fare programmi molto al di sopra del tuo livello (ho passato anni a farlo), ti confonderai e commetterai errori. Grandi errori come quelli in cui improvvisamente ti rendi conto che la tua soluzione non può funzionare, quando finalmente capisci il problema, e devi apportare modifiche così complicate che potrebbero impedirti di risolvere il tuo problema o rendere il codice terribile. TDD è per questi casi, credo. Sai che non affronti il problema che stai affrontando e quindi metti test ovunque per assicurarti di avere una base solida. Il TDD non risolve la visione di 10.000 piedi, però. Potresti camminare sempre in cerchio con un codice perfettamente pulito.
Tuttavia, se provi a fare qualcosa di nuovo ma che è appena sopra il tuo livello, potresti ottenere il tuo programma perfetto o quasi perfetto. Penso che sia davvero difficile sapere quali sono i programmi nella tua "frontiera della conoscenza", ma in teoria è il modo migliore per imparare. In realtà, riscrivo molto i programmi da zero. Alcune persone lo fanno, ma hai bisogno di molto tempo e pazienza perché la terza volta che ripeti un programma non banale non ti ecciti come la prima volta.
Quindi il mio consiglio è: non pensare di aver capito qualcosa fino a quando non puoi scrivere un programma privo di bug proprio per quella cosa. E poi prova a combinare due di quei concetti che conosci profondamente nello stesso programma. Sono quasi sicuro che riuscirai a farlo bene la prima volta. Uno dei modi migliori è quello di riscrivere software non banale, cosa che per la prima volta è stato un grande sforzo (lo sto facendo ora con le app Android). Ogni volta che ricomincio cambio qualcosa o aggiungo qualcosa, solo per aggiungere un po 'di divertimento, e posso dirti che sto migliorando sempre meglio ... forse non privo di bug ma davvero orgoglioso.