Comment créer une chaîne Python multiligne avec des variables en ligne?

95

Je recherche un moyen propre d'utiliser des variables dans une chaîne Python multiligne. Dites que je voulais faire ce qui suit:

string1 = go
string2 = now
string3 = great

"""
I will $string1 there
I will go $string2
$string3
"""

Je cherche à voir s'il y a quelque chose de similaire à $Perl pour indiquer une variable dans la syntaxe Python.

Sinon, quelle est la manière la plus propre de créer une chaîne multiligne avec des variables?

évolution
la source

Réponses:

156

Le moyen commun est la format()fonction:

>>> s = "This is an {example} with {vars}".format(vars="variables", example="example")
>>> s
'This is an example with variables'

Cela fonctionne bien avec une chaîne de format multiligne:

>>> s = '''\
... This is a {length} example.
... Here is a {ordinal} line.\
... '''.format(length='multi-line', ordinal='second')
>>> print(s)
This is a multi-line example.
Here is a second line.

Vous pouvez également passer un dictionnaire avec des variables:

>>> d = { 'vars': "variables", 'example': "example" }
>>> s = "This is an {example} with {vars}"
>>> s.format(**d)
'This is an example with variables'

La chose la plus proche de ce que vous avez demandé (en termes de syntaxe) sont les chaînes de modèle . Par exemple:

>>> from string import Template
>>> t = Template("This is an $example with $vars")
>>> t.substitute({ 'example': "example", 'vars': "variables"})
'This is an example with variables'

Je dois ajouter cependant que la format()fonction est plus courante car elle est facilement disponible et ne nécessite pas de ligne d'importation.

Siméon Visser
la source
2
Pourrait utiliser vars()ou locals()comme dictionnaire en question
Ismail Badawi
2
@isbadawi Explicit est meilleur qu'implicite. Mieux vaut ne transmettre que les variables dont vous avez besoin. Si vous ne savez pas ce dont vous avez besoin, car la chaîne est fournie par l'utilisateur, les "variables" devraient de toute façon être des éléments dans un dict.
agf
La deuxième solution est l'OMI la plus propre. Le dictionnaire ainsi que le nom de la variable claire du dictionnaire dans la piqûre multiligne. J'utiliserai cette méthode. Merci. Des tas de bonnes réponses ci-dessous aussi mais c'était parfait.
évolution
@SimeonVisser, "string" .format (...) n'est pas valide sur les anciennes versions de python (par exemple 2.4)
Oz123
Si vous utilisez des accolades, elles doivent être échappées comme {{this}}.
Jonny
52

REMARQUE : La méthode recommandée pour mettre en forme une chaîne en Python est d'utiliser format(), comme indiqué dans la réponse acceptée . Je préserve cette réponse comme exemple de la syntaxe de style C qui est également prise en charge.

# NOTE: format() is a better choice!
string1 = "go"
string2 = "now"
string3 = "great"

s = """
I will %s there
I will go %s
%s
""" % (string1, string2, string3)

print(s)

Quelques lectures:

David Cain
la source
2
Ce n'est pas vraiment la même chose car l'OP veut des paramètres nommés, pas des paramètres positionnels.
Ismail Badawi
1
C'est toujours une bonne solution, et pour une interpolation multiligne, c'est plus direct. Vous n'avez rien à importer et il utilise une interpolation Python régulière.
unflores
4
" Vous auriez probablement pu répondre à celui-ci avec un peu de googler " Ce qui implique que nous n'avons pas trouvé ce message après googler ...
Stevoisiak
30

Vous pouvez utiliser les f-strings de Python 3.6 pour les variables à l'intérieur de chaînes multilignes ou de longues chaînes simples. Vous pouvez spécifier manuellement les caractères de nouvelle ligne à l'aide de \n.

Variables dans une chaîne multiligne

string1 = "go"
string2 = "now"
string3 = "great"

multiline_string = (f"I will {string1} there\n"
                    f"I will go {string2}.\n"
                    f"{string3}.")

print(multiline_string)

J'irai là-bas
j'irai maintenant
super

Variables dans une longue chaîne sur une seule ligne

string1 = "go"
string2 = "now"
string3 = "great"

singleline_string = (f"I will {string1} there. "
                     f"I will go {string2}. "
                     f"{string3}.")

print(singleline_string)

Je vais y aller. Je vais y aller maintenant. génial.


Vous pouvez également créer une chaîne F multiligne avec des guillemets triples.

multiline_string = f"""I will {string1} there.
I will go {string2}.
{string3}."""
Stevoisiak
la source
Cela garde votre code source joli, et dans pré-Python3.6, vous pouvez obtenir le même effet simplement en faisant cela (jeu supplémentaire de parenthèses et utilisation +pour concaténer): stackoverflow.com/a/54564926/4561887
Gabriel Staples
Les citations triples sont largement préférées. Vous devez d'abord présenter ce formulaire.
jpmc26
@ jpmc26 J'ai d'abord présenté le style parenthèse basé sur les directives de PEP 8 pour l'indentation du code . Pourquoi le triple devis serait-il préférable?
Stevoisiak
10

Voici ce que tu veux:

>>> string1 = "go"
>>> string2 = "now"
>>> string3 = "great"
>>> mystring = """
... I will {string1} there
... I will go {string2}
... {string3}
... """
>>> locals()
{'__builtins__': <module '__builtin__' (built-in)>, 'string3': 'great', '__package__': None, 'mystring': "\nI will {string1} there\nI will go {string2}\n{string3}\n", '__name__': '__main__', 'string2': 'now', '__doc__': None, 'string1': 'go'}
>>> print(mystring.format(**locals()))

I will go there
I will go now
great
Havok
la source
Notez que les guillemets triples """préservent les nouvelles lignes, ce qui signifie qu'il y a une nouvelle ligne supplémentaire avant et aprèsmystring
Stevoisiak
Vous pouvez utiliser .strip(), .rstrip()ou .lstrip(), ou ue un jeu entre les guillemets triples pour éviter de créer une nouvelle ligne. mystring = "" "\ ABC \" ""
Havok
6

Un dictionnaire peut être passé à format(), chaque nom de clé deviendra une variable pour chaque valeur associée.

dict = {'string1': 'go',
        'string2': 'now',
        'string3': 'great'}

multiline_string = '''I'm will {string1} there
I will go {string2}
{string3}'''.format(**dict)

print(multiline_string)


Une liste peut également être transmise format(), le numéro d'index de chaque valeur sera utilisé comme variable dans ce cas.

list = ['go',
        'now',
        'great']

multiline_string = '''I'm will {0} there
I will go {1}
{2}'''.format(*list)

print(multiline_string)


Les deux solutions ci-dessus donneront le même résultat:

J'irai là-bas
j'irai maintenant
super

bouffon
la source
0

Si quelqu'un est venu ici du client python-graphql à la recherche d'une solution pour passer un objet en tant que variable, voici ce que j'ai utilisé:

query = """
{{
  pairs(block: {block} first: 200, orderBy: trackedReserveETH, orderDirection: desc) {{
    id
    txCount
    reserveUSD
    trackedReserveETH
    volumeUSD
  }}
}}
""".format(block=''.join(['{number: ', str(block), '}']))

 query = gql(query)

Assurez-vous d'échapper à toutes les accolades comme je l'ai fait: "{{", "}}"

Radu Ciobanu
la source
0

Les chaînes f , également appelées «littéraux de chaîne formatés», sont des littéraux de chaîne qui ont un fau début; et des accolades contenant des expressions qui seront remplacées par leurs valeurs.

Les chaînes f sont évaluées au moment de l'exécution.

Ainsi, votre code peut être réécrit comme:

string1="go"
string2="now"
string3="great"
print(f"""
I will {string1} there
I will go {string2}
{string3}
""")

Et cela évaluera à:

I will go there
I will go now
great

Vous pouvez en savoir plus ici .

Anshika Singh
la source