O Python importa um grande número de arquivos na inicialização:
% python -c 'import sys; print len(sys.modules)'
39
Cada um deles requer um número ainda maior de tentativas de abrir um arquivo Python, porque há muitas maneiras de definir um módulo:
% python -vv -c 'pass'
# installing zipimport hook
import zipimport # builtin
# installed zipimport hook
# trying site.so
# trying sitemodule.so
# trying site.py
# trying site.pyc
# trying /System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site.so
# trying /System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/sitemodule.so
# trying /System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site.py
# /System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site.pyc matches /System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site.py
import site # precompiled from /System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site.pyc
# trying os.so
# trying osmodule.so
# trying os.py
# trying os.pyc
# trying /System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/os.so
# trying /System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/osmodule.so
# trying /System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/os.py
# /System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/os.pyc matches /System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/os.py
import os # precompiled from /System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/os.pyc
...
Cada "tentativa", exceto aquelas que são incorporadas, requer chamadas do sistema em nível de sistema operacional, e cada "importação" parece acionar cerca de 8 mensagens "que estão tentando". (Havia maneiras de reduzir isso usando zipimport, e cada caminho em seu PYTHONPATH pode exigir outra chamada.)
Isso significa que há quase 200 chamadas de sistema stat antes do Python iniciar na minha máquina, e "time" atribui isso a "sys" ao invés de "user", porque o programa do usuário está aguardando o sistema para fazer as coisas. p>
Em comparação, e como o terdon disse, "bc" não tem esse custo inicial alto. Olhando para a saída dtruss (eu tenho um Mac; "strace" para um sistema operacional baseado em Linux), vejo que bc não faz nenhuma chamada de sistema open () ou stat (), exceto por carregar alguns compartilhados as bibliotecas são o começo, o que é claro que o Python também faz. Além disso, o Python tem mais arquivos para ler, antes de estar pronto para processar qualquer coisa.
Esperar pelo disco é lento.
Você pode ter uma noção do custo de inicialização do Python fazendo:
time python -c pass
São 0,032s na minha máquina, enquanto 'print 6 ** 6 ** 6' é 0,072s, então o custo de inicialização é 1/2 do tempo total e o cálculo + conversão em decimal é a outra metade. Enquanto:
time echo 1 | bc
leva 0,005s, e "6 ^ 6 ^ 6" leva 0,184s, então a exponenciação do bc é 4x mais lenta que a do Python mesmo que seja 7x mais rápida para começar.