Windows: avoid importing encodings._win_cp_codecs and time at startup

Aberta Para iniciantes
#161,510 0 comentários 0 reações 0 responsáveis Ver no GitHub

Mantenedores costumam responder em até 1 dia

Ninguém assumiu esta issue ainda.

Avaliação

Dificuldade
2/5
Tempo estimado
1-3 horas
Facilidade para iniciantes
82/100
Tipo de issue
Funcionalidade
Clareza
Claramente especificada
Status de atividade
Ativa
Stack de tecnologia
python
Domínio
performance

Direção de pesquisa

A issue identifica Lib/encodings/__init__.py e Lib/zipimport.py; leia os dois pontos de importação e seu uso em win32_code_page_search_function e _parse_dostime. Compare as importações feitas durante a inicialização no Windows e execute os testes indicados de codec, zipimport, time, signal e sys. O trabalho estará concluído quando as duas importações forem adiadas até seus pontos de uso e o comportamento de inicialização melhorar sem regressões nos testes.

Escrita pelo modelo de indexação a partir do texto da issue.

Descrição

OS-windows performance stdlib type-feature
Feature or enhancement

On Windows, python -c pass imports two modules that Linux doesn't, and neither is needed on most starts:

  • encodings/__init__.py imports create_win32_code_page_codec from encodings._win_cp_codecs at module level (since 3.14). It is only called from win32_code_page_search_function, for a cpNNN name with no codec module.
  • zipimport imports time at module level for time.mktime in _parse_dostime. On Windows, time module init runs _tzset, which calls GetTimeZoneInformation. The first call in a process costs about 1 ms here.

From -X importtime (3.14.4, self time, median of 15): _win_cp_codecs 0.5 ms, time 0.96 ms on Windows (0.07 ms on Linux).

Moving both imports into the functions that use them (patch below) made python -c pass 3.6 ms faster (38.4 -> 34.4 ms; 95% CI 3.1-4.2 ms over 300 interleaved runs, release build of 3.14.4 without PGO). Each change alone is worth about 2 ms (_win_cp_codecs 2.1, time 2.4).

test_codecs, test_zipimport, test_zipimport_support, test_time, test_signal and test_sys pass with the change (3.14.4 build).

Both imports are unchanged on main (2781ffe1f2). The change, against main:

patch
diff --git a/Lib/encodings/__init__.py b/Lib/encodings/__init__.py
index 04594ea..bbccb93 100644
--- a/Lib/encodings/__init__.py
+++ b/Lib/encodings/__init__.py
@@ -157,8 +157,6 @@ def search_function(encoding):
 codecs.register(search_function)
 
 if sys.platform == 'win32':
-    from ._win_cp_codecs import create_win32_code_page_codec
-
     def win32_code_page_search_function(encoding):
         encoding = encoding.lower()
         if not encoding.startswith('cp'):
@@ -173,6 +171,7 @@ if sys.platform == 'win32':
         except (OverflowError, OSError):
             return None
 
+        from ._win_cp_codecs import create_win32_code_page_codec
         return create_win32_code_page_codec(cp)
 
     codecs.register(win32_code_page_search_function)
diff --git a/Lib/zipimport.py b/Lib/zipimport.py
index 09a85f6..aae77df 100644
--- a/Lib/zipimport.py
+++ b/Lib/zipimport.py
@@ -16,7 +16,6 @@ import _frozen_importlib as _bootstrap  # for _verbose_message
 import _imp  # for check_hash_based_pycs
 import _io  # for open
 import marshal  # for loads
-import time  # for mktime
 
 __all__ = ['ZipImportError', 'zipimporter']
 
@@ -767,6 +766,8 @@ def _compile_source(pathname, source, module):
 # Convert the date/time values found in the Zip archive to a value
 # that's compatible with the time stamp stored in .pyc files.
 def _parse_dostime(d, t):
+    # Imported here: importing time at start-up costs a time zone lookup.
+    import time
     return time.mktime((
         (d >> 9) + 1980,    # bits 9..15: year
         (d >> 5) & 0xF,     # bits 5..8: month

I used GitHub Copilot (Claude Opus 5.5 model) to trace this, build and time the prototype, and draft this issue. The measurements were run on my machine.

Has this already been discussed elsewhere?

This is a minor feature, which does not need previous discussion elsewhere

Links to previous discussion of this feature:

No response

Linguagem predominante
Python
Estrelas
77.9k
Forks
37.1k
Merge médio
17h 43min
PRs com merge (30d)
675

Preparar o ambiente

Abrir no Codespaces

Inicia o contêiner de desenvolvimento do projeto no navegador, com a sua própria conta do GitHub.

Primeiros passos

  1. Leia a issue inteira e depois o guia de contribuição do projeto.
  2. Comente na issue dizendo que vai assumir — evita que duas pessoas façam o mesmo trabalho.
  3. Faça um fork do repositório e trabalhe em uma branch.
  4. Abra um pull request que referencie o número da issue.

Mais de python/cpython

Todas as issues de python/cpython

Issues semelhantes

Mais issues de Python

Receba novas issues na sua caixa de entrada

Um resumo curto de issues do GitHub para quem está começando.