Empresas
Empleos
  • Sobre nosotros
  • Soluciones
    • Publicación de vacantes
      Publica tu vacante y recibe candidatos calificados en 48h.
    • Evaluación de candidatos
      500+ pruebas técnicas y psicológicas, más anti-fraude.
    • Headhunting
      Búsqueda ejecutiva a la medida de principio a fin.
    • Nómina + EOR
      Dispersión de nómina y EOR en más de 15 países de LATAM.
  • Precios
  • Empleos

0

161
Vistas
¿Cómo posponer/diferir la evaluación de f-strings?

Estoy usando cadenas de plantillas para generar algunos archivos y me encanta la concisión de las nuevas cadenas f para este propósito, para reducir mi código de plantilla anterior de algo como esto:

 template_a = "The current name is {name}" names = ["foo", "bar"] for name in names: print (template_a.format(**locals()))

Ahora puedo hacer esto, reemplazando directamente las variables:

 names = ["foo", "bar"] for name in names: print (f"The current name is {name}")

Sin embargo, a veces tiene sentido tener la plantilla definida en otro lugar: más arriba en el código, o importada de un archivo o algo así. Esto significa que la plantilla es una cadena estática con etiquetas de formato. Algo tendría que pasarle a la cadena para decirle al intérprete que interprete la cadena como una nueva cadena f, pero no sé si existe tal cosa.

¿Hay alguna forma de traer una cadena y hacer que se interprete como una cadena f para evitar usar la .format(**locals()) ?

Idealmente, quiero poder codificar así... (donde magic_fstring_function es donde entra la parte que no entiendo):

 template_a = f"The current name is {name}" # OR [Ideal2] template_a = magic_fstring_function(open('template.txt').read()) names = ["foo", "bar"] for name in names: print (template_a)

... con esta salida deseada (sin leer el archivo dos veces):

 The current name is foo The current name is bar

... pero el resultado real que obtengo es:

 The current name is {name} The current name is {name}
over 4 years ago · Santiago Trujillo
3 Respuestas
Responde la pregunta

0

Aquí tienes un "Ideal 2" completo.

No es un f-string, ni siquiera usa f-strings, pero hace lo solicitado. Sintaxis exactamente como se especifica. No hay dolores de cabeza de seguridad ya que no estamos usando eval() .

Utiliza una pequeña clase e implementa __str__ , que se llama automáticamente por impresión. Para escapar del alcance limitado de la clase, usamos el módulo de inspect para saltar un cuadro hacia arriba y ver las variables a las que tiene acceso la persona que llama.

 import inspect class magic_fstring_function: def __init__(self, payload): self.payload = payload def __str__(self): vars = inspect.currentframe().f_back.f_globals.copy() vars.update(inspect.currentframe().f_back.f_locals) return self.payload.format(**vars) template = "The current name is {name}" template_a = magic_fstring_function(template) # use it inside a function to demonstrate it gets the scoping right def new_scope(): names = ["foo", "bar"] for name in names: print(template_a) new_scope() # The current name is foo # The current name is bar
over 4 years ago · Santiago Trujillo Denunciar

0

Una forma concisa de evaluar una cadena como una cadena f (con todas sus capacidades) es usar la siguiente función:

 def fstr(template): return eval(f"f'{template}'")

Entonces puedes hacer:

 template_a = "The current name is {name}" names = ["foo", "bar"] for name in names: print(fstr(template_a)) # The current name is foo # The current name is bar

Y, a diferencia de muchas otras soluciones propuestas, también puede hacer:

 template_b = "The current name is {name.upper() * 2}" for name in names: print(fstr(template_b)) # The current name is FOOFOO # The current name is BARBAR
over 4 years ago · Santiago Trujillo Denunciar

0

Esto significa que la plantilla es una cadena estática con etiquetas de formato.

Sí, esa es exactamente la razón por la que tenemos literales con campos de reemplazo y .format , para que podamos reemplazar los campos cuando queramos llamando a format en él.

Algo tendría que pasarle a la cadena para decirle al intérprete que interprete la cadena como una nueva cadena f

Ese es el prefijo f/F . Podría envolverlo en una función y posponer la evaluación durante el tiempo de la llamada, pero por supuesto eso genera una sobrecarga adicional:

 template_a = lambda: f"The current name is {name}" names = ["foo", "bar"] for name in names: print (template_a())

Que imprime:

 The current name is foo The current name is bar

pero se siente mal y está limitado por el hecho de que solo puede mirar el espacio de nombres global en sus reemplazos. Intentar usarlo en una situación que requiere nombres locales fallará miserablemente a menos que se pase a la cadena como argumentos (lo que supera totalmente el punto).

¿Hay alguna forma de traer una cadena y hacer que se interprete como una cadena f para evitar usar la .format(**locals()) ?

Aparte de una función (limitaciones incluidas), no, también podría quedarse con .format .

over 4 years ago · Santiago Trujillo Denunciar
Responde la pregunta
Encuentra empleos remotos

¡Descubre la nueva forma de encontrar empleo!

Top de empleos
Top categorías de empleo
Empresas
Publicar vacante Precios Comercial
Legal
Términos y condiciones Política de privacidad
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomiéndame algunas ofertas
Necesito ayuda