Как я могу напечатать буквенные фигурные скобки в строке Python, а также использовать .format на нем?

1512
x = " \{ Hello \} {0} "
print(x.format(42))

дает мне : Key Error: Hello\\

Я хочу напечатать вывод: {Hello} 42

Schitti
источник
1
Смотрите также: stackoverflow.com/questions/35574349
dreftymac
9
Для тех, кто хочет избежать двойных скобок ( {{ }}), используйте string.Template. Там вы подставляете идентификаторы формы $foo(удобно для генерации кода LaTeX).
Иоаннис Филиппидис
Для тех, кто хочет избежать удвоения фигурных скобок и не против добавления другой зависимости в свои проекты Python, есть также Jinja2, который окончательно решает эту проблему, разрешая определенный пользователем синтаксис-разделитель.
dreftymac

Ответы:

2072

Вам нужно удвоить {{и }}:

>>> x = " {{ Hello }} {0} "
>>> print(x.format(42))
' { Hello } 42 '

Вот соответствующая часть документации Python для синтаксиса строки формата :

Строки формата содержат «замещающие поля», заключенные в фигурные скобки {} . Все, что не содержится в фигурных скобках, считается буквальным текстом, который копируется без изменений в выходные данные. Если вам нужно включить символ скобки в буквальный текст, его можно избежать путем удвоения: {{и }}.

Грег Хьюгилл
источник
264
Так что если вы хотите напечатать "{42}", вы бы использовали "{{{0}}}".format(42)!
Хьюз
7
А что, если вы хотите одну фигурную скобку? "{ something { } {value}".format(42)не работает
AJP
14
"{{" .format () и "}}". format () выводить одиночные фигурные скобки. В вашем примере: выведите «{{thing {{}} {0}». Формат (42) выведет «{что-то {} 42».
Марк Виссер
2
Что {0}значит?
CodyBugstein
6
@Imray: {0}относится к первому аргументу .format(). Вы можете напечатать более одного значения, например, {0} {1} {2}если вы даете одинаковое количество аргументов .format(). Смотрите подробные примеры на docs.python.org/library/string.html#format-examples .
Грег Хьюгилл
74

Вы избежите этого, удвоив скобки.

Например:

x = "{{ Hello }} {0}"
print(x.format(42))
Камил Кисиэль
источник
60

Python 3.6+ (2017)

В последних версиях Python можно использовать f-строки (см. Также PEP498 ).

С f-струнами следует использовать двойной {{или}}

n = 42  
print(f" {{Hello}} {n} ")

производит желаемое

 {Hello} 42

Если вам нужно разрешить выражение в скобках вместо использования литерального текста, вам понадобится три набора скобок:

hello = "HELLO"
print(f"{{{hello.lower()}}}")

производит

{hello}
divenex
источник
46

ОП написал этот комментарий:

Я пытался отформатировать небольшой JSON для некоторых целей, например: '{"all": false, "selected": "{}"}'.format(data)чтобы получить что-то вроде{"all": false, "selected": "1,2"}

Довольно часто возникает проблема с «выходящими скобками» при работе с JSON.

Я предлагаю сделать это:

import json
data = "1,2"
mydict = {"all": "false", "selected": data}
json.dumps(mydict)

Это чище, чем альтернатива, которая:

'{{"all": false, "selected": "{}"}}'.format(data)

Использование jsonбиблиотеки определенно предпочтительнее, когда строка JSON становится более сложной, чем в примере.

twasbrillig
источник
1
Аминь! Это может показаться чем-то большим, но использование библиотек для выполнения того, что библиотеки должны делать, а не для срезания углов ... делает лучше.
Каолин Огонь
1
Но порядок ключей в объекте Python не гарантирован ... Тем не менее, библиотека JSON гарантированно сериализуется в формате JSON.
wizzwizz4
2
wizzwizz4: Хороший вопрос. Начиная с Python 3.6, словари упорядочены по принципу вставки, так что это не будет проблемой. Версии Python между 2.7 и 3.5 могут использовать OrderedDict из библиотеки коллекций.
twasbrillig
24

Попробуйте сделать это:

x = " {{ Hello }} {0} "
print x.format(42)
DNR
источник
14

Хотя не лучше, просто для справки, вы также можете сделать это:

>>> x = '{}Hello{} {}'
>>> print x.format('{','}',42)
{Hello} 42

Это может быть полезно, например, когда кто-то хочет напечатать {argument}. Это может быть более читабельным, чем'{{{}}}'.format('argument')

Обратите внимание, что вы опускаете позиции аргументов (например, {}вместо {0}) после Python 2.7

Джордж Априлис
источник
5

Если вы собираетесь делать это много, было бы неплохо определить вспомогательную функцию, которая позволит вам вместо этого использовать произвольные заменители скобок, например

def custom_format(string, brackets, *args, **kwargs):
    if len(brackets) != 2:
        raise ValueError('Expected two brackets. Got {}.'.format(len(brackets)))
    padded = string.replace('{', '{{').replace('}', '}}')
    substituted = padded.replace(brackets[0], '{').replace(brackets[1], '}')
    formatted = substituted.format(*args, **kwargs)
    return formatted

>>> custom_format('{{[cmd]} process 1}', brackets='[]', cmd='firefox.exe')
'{{firefox.exe} process 1}'

Обратите внимание, что это будет работать либо со скобками, являющимися строкой длины 2, либо с итерацией из двух строк (для многосимвольных разделителей).

tvt173
источник
Мысль об этом тоже. Конечно, это тоже будет работать, и алгоритм проще. Но представьте, что у вас много такого текста, и вы просто хотите параметризовать его здесь и там. Каждый раз, когда вы создаете входную строку, вы не захотите заменять все эти скобки вручную. Вы просто хотели бы «вставить» ваши параметризации здесь и там. В этом случае, я думаю, что этот метод и легче думать, и выполнять с точки зрения пользователя. Я был вдохновлен командой linux 'sed', которая имеет аналогичные возможности произвольно выбирать разделитель в зависимости от того, что удобно.
tvt173
Короче говоря, я бы предпочел, чтобы функция полезности была немного более сложной, чем если бы @ $$ каждый раз использовал боль. Пожалуйста, дайте мне знать, если я неправильно понял ваше предложение.
tvt173
Я пошел дальше и добавил короткую демонстрацию в мой public.lab space github.com/dreftymac/public.lab/blob/master/topic/python/…
dreftymac
3

Я недавно столкнулся с этим, потому что я хотел вставить строки в предварительно отформатированный JSON. Моим решением было создать вспомогательный метод, например так:

def preformat(msg):
    """ allow {{key}} to be used for formatting in text
    that already uses curly braces.  First switch this into
    something else, replace curlies with double curlies, and then
    switch back to regular braces
    """
    msg = msg.replace('{{', '<<<').replace('}}', '>>>')
    msg = msg.replace('{', '{{').replace('}', '}}')
    msg = msg.replace('<<<', '{').replace('>>>', '}')
    return msg

Затем вы можете сделать что-то вроде:

formatted = preformat("""
    {
        "foo": "{{bar}}"
    }""").format(bar="gas")

Получает работу, если производительность не является проблемой.

Кристьян Валур
источник
Простой И элегантный для интеграции в существующий код с небольшими изменениями. Спасибо!
Column01
2

Если вам нужно сохранить две фигурные скобки в строке, вам нужно 5 фигурных скобок с каждой стороны переменной.

>>> myvar = 'test'
>>> "{{{{{0}}}}}".format(myvar)
'{{test}}'
Ричард
источник
Для тех, кто использует f-струны, используйте 4 фигурные скобки с каждой стороны вместо 5
TerryA
0

Причина в том, {}что синтаксис .format()так в вашем случае .format()не распознает, {Hello}поэтому выдает ошибку.

вы можете переопределить его, используя двойные фигурные скобки {{}},

x = " {{ Hello }} {0} "

или

попробуйте %sдля форматирования текста,

x = " { Hello } %s"
print x%(42)  
Мохидин бен Мухаммед
источник
0

Я наткнулся на эту проблему при попытке напечатать текст, который я могу скопировать вставить в латексный документ. Я расширяю этот ответ и использую именованные поля замены:

Допустим, вы хотите распечатать продукт из нескольких переменных с такими индексами, как введите описание изображения здесь, например , в Latex $A_{ 0042 }*A_{ 3141 }*A_{ 2718 }*A_{ 0042 }$ . Следующий код выполняет работу с именованными полями, так что для многих индексов он остается читабельным:

idx_mapping = {'i1':42, 'i2':3141, 'i3':2178 }
print('$A_{{ {i1:04d} }} * A_{{ {i2:04d} }} * A_{{ {i3:04d} }} * A_{{ {i1:04d} }}$'.format(**idx_mapping))
v.tralala
источник
-1

Если вы хотите напечатать только одну фигурную скобку (например {), вы можете использовать ее {{, и вы можете добавить больше фигурных скобок позже в строку, если хотите. Например:

>>> f'{{ there is a curly brace on the left. Oh, and 1 + 1 is {1 + 1}'
'{ there is a curly brace on the left. Oh, and 1 + 1 is 2'
Луис Кабрера Бенито
источник
-1

Когда вы просто пытаетесь интерполировать строки кода, я бы предложил использовать jinja2, который является полнофункциональным механизмом шаблонов для Python, то есть:

from jinja2 import Template

foo = Template('''
#include <stdio.h>

void main() {
    printf("hello universe number {{number}}");
}
''')

for i in range(2):
    print(foo.render(number=i))

Таким образом, вы не будете вынуждены дублировать фигурные скобки, как целая куча других ответов

BPL
источник
-3

Вы можете сделать это, используя метод необработанной строки, просто добавив символ «r» без кавычек перед строкой.

# to print '{I am inside braces}'
print(r'{I am inside braces}')
Суровый Аггарвал
источник
Здравствуйте! Вы могли бы хотеть перепроверить это; Python 3.7 отпечатков \{I am inside braces\}.
Теодор
1
@ Теодор, прости за это. Теперь я исправил это, напечатав как необработанную строку.
Суровый Аггарвал