Dois conceitos podem nos ajudar a entender melhor por que o Python compilado no código de máquina nativo "pode" não ser executado tão rápido quanto o C compilado ou outras linguagens comumente compiladas. Eles são chamados de ligação antecipada e ligação tardia.
Eu deveria começar dizendo que não sou especialista em Python e vim a este site por acidente. Mas eu gosto deste site.
Conforme mencionado em outra resposta aqui, o compilador C ++ pode saber muito sobre o programa e tomar decisões sobre quais operações usar para estruturas de dados específicas. Como exemplo, se duas variáveis inteiras precisarem ser adicionadas, o compilador sabe que são inteiros nativos, com 32 bits de largura, por exemplo, e pode adicioná-los juntamente com uma instrução "ADD". Por isso, compila a instrução ADD no código. Ele está bloqueado e não pode ser alterado enquanto o programa está sendo executado. Isso é obrigatório.
Por outro lado, em uma linguagem como Python, podemos esperar que o programa junte diferentes tipos de dados de maneiras complexas. Agora, o compilador não sabe se nossas 2 variáveis são números inteiros, flutuantes, strings ou listas. Portanto, ele precisa compilar o código que determina essas informações no tempo de execução e selecionar a operação correta enquanto o programa está sendo executado. Isso é uma ligação tardia e podemos entender que haverá um impacto no desempenho para realizar esse trabalho extra enquanto o programa estiver em execução. É o preço que você paga por manter essas opções abertas em uma linguagem como Python, mas fornece flexibilidade máxima em tempo de execução.