Conversia formatului în Python, format (umplere cu zero, notație exponențială, hexazecimal, etc.)

Afaceri

Pentru a converti (formata) un număr sau un șir de caractere în diferite formate în Python, utilizați funcția încorporată format() sau metoda string str.format().

În această secțiune, vom explica modul de utilizare a următoarelor funcții.

  • funcție încorporată (de exemplu, în limbajul de programare)format()
  • metoda șirului de caracterestr.format()

În plus, șirul de specificații de format pentru conversia în următorul format este explicat cu un cod de exemplu.

  • Justificat la stânga, Justificat la centru, Justificat la dreapta
  • umplere zero
  • Semn (plus sau minus)
  • Separator de cifre (virgulă, subliniere)
  • Numere binare, octale și hexazecimale
  • Specificați numărul de cifre după punctul zecimal
  • Cifre semnificative (numărul de cifre semnificative)
  • notație exponențială
  • Afișare procentuală

Rețineți că, începând cu Python 3.6, șirurile de caractere f (f-strings) au fost adăugate la metoda string str.format() pentru a o face mai concisă.

Funcție încorporată: format()

format() este furnizat ca o funcție standard încorporată în Python.

Schema este următoarea.

  • format(value, format_spec)
    • Primul argument: valoareavalue
      Valoarea inițială. Șir de caractere str, număr int, float, etc.
    • Al doilea argumentformat_spec
      Șir de caractere de specificare a formatului. Șir str
    • Valoarea returnată: un șir de caractere formatat str

Exemplele sunt prezentate mai jos. Tipurile de șiruri de formate și modul de scriere a acestora sunt descrise ulterior.

În acest exemplu, am utilizat ca prim argument literali numerici și literali de tip șir de caractere, dar, desigur, puteți utiliza variabile care conțin aceste valori.

s = format(255, '04x')
print(s)
print(type(s))
# 00ff
# <class 'str'>

print(format('center', '*^16'))
# *****center*****

Metoda String str.format()

Există, de asemenea, o metodă format() pentru tipul string str.

{} din șirul str care apelează metoda format() se numește câmp de substituție și este înlocuit cu argumentul metodei format().

Șirul de specificații de format trebuie scris în câmpul de substituție {} urmat de „:”.

Valoarea de returnare este un șir de caractere formatat str.

Procesul echivalent cu funcția încorporată format() descrisă mai sus este următorul.

s = '{:04x}'.format(255)
print(s)
print(type(s))
# 00ff
# <class 'str'>

print('{:*^16}'.format('center'))
# *****center*****

Din nou, folosim ca argumente literali numerici și literali de tip șir de caractere, dar, bineînțeles, sunt acceptate și variabilele.

Specificarea argumentelor pentru câmpurile de substituție

Specificați argumentele în ordine (implicit)

Pot exista mai multe câmpuri de substituție {} și, în mod implicit, argumentele metodei sunt procesate în ordine. Dacă șirul de specificații de format din {} este omis, acesta va fi convertit într-un șir de caractere de către str().

Util pentru a introduce valori variabile într-un șir de caractere și pentru a le imprima.

print('{}-{}-{}'.format('100', '二百', 300))
# 100-二百-300

Specificați un argument pozițional pentru valori întregi

În cazul în care se specifică o valoare întreagă în {}, cum ar fi {0} sau {1}, rezultatul va depinde de ordinea argumentelor. Același număr poate fi utilizat în mod repetat. Acest lucru este util atunci când doriți să inserați aceeași valoare într-un șir de caractere.

print('{0}-{1}-{0}'.format('foo', 'bar'))
# foo-bar-foo

Specificați argumente de cuvinte cheie pentru nume arbitrare (șiruri de caractere)

De asemenea, puteți specifica orice nume în {} și îl puteți introduce ca argument de cuvânt cheie.

print('{day}/{month}/{year}/'.format(day=11, month=1, year=2018))
# 11/1/2018

Specificați o listă sau un dicționar ca argument

Listele și dicționarele pot fi specificate ca argumente.

Utilizați [] pentru a specifica indicele unei liste sau cheia unui dicționar într-un câmp de substituție. Rețineți că ghilimelele „'” și „” nu se utilizează pentru a specifica cheile de dicționar.

Dacă doriți să utilizați același argument în mod repetat, trebuie să specificați o valoare întreagă sau un șir de caractere (nume), așa cum este descris mai sus.

l = ['one', 'two', 'three']
print('{0[0]}-{0[1]}-{0[2]}'.format(l))
# one-two-three

d1 = {'name': 'Alice', 'age': 20}
d2 = {'name': 'Bob', 'age': 30}
print('{0[name]} is {0[age]} years old.\n{1[name]} is {1[age]} years old.'.format(d1, d2))
# Alice is 20 years old.
# Bob is 30 years old.

Acesta poate fi extins ca argument pozițional, adăugând * la listă și specificându-l ca argument, sau ca argument de tip cuvânt cheie, adăugând ** la dicționar și specificându-l ca argument.

l = ['one', 'two', 'three']
print('{}-{}-{}'.format(*l))
# one-two-three

d = {'name': 'Alice', 'age': 20}
print('{name} is {age} years old.'.format(**d))
# Alice is 20 years old.

Descrierea parantezelor curly brackets {}

Dacă doriți să scrieți paranteze {,} în metoda format(), repetați de două ori ca {{,}}. Rețineți că backslash-urile nu pot fi scăpate.

print('{{}}-{num}-{{{num}}}'.format(num=100))
# {}-100-{100}

șir formatat

În ambele cazuri, pentru a specifica formatul, scrieți „:format string” după valoarea întreagă sau șirul de nume în {}.

print('{num:x}'.format(num=255))
# ff

print('{day}/{month:02}/{year:02}/'.format(day=11, month=1, year=2018))
# 11/01/2018

În cele ce urmează, vom explica cum se specifică formatul folosind un șir de format. Codul de exemplu utilizează metoda string str.format(), dar același șir de format poate fi utilizat cu funcția încorporată format(). În funcția încorporată format(), șirul de specificare a formatului este specificat ca al doilea argument.

Justificat la stânga, Justificat la centru, Justificat la dreapta

Puteți alinia stânga-justificat, centru-justificat, dreapta-justificat etc. mai jos. Specificați numărul total de caractere sub formă de număr.

  • <
  • ^
  • >
print('left  : {:<10}'.format(100))
print('center: {:^10}'.format(100))
print('right : {:>10}'.format(100))
# left  : 100       
# center:    100    
# right :        100

De asemenea, puteți specifica un caracter care trebuie completat. Dacă este omis, ca în exemplul de mai sus, acesta este un spațiu.

Puteți utiliza caractere cu două octeți, atâta timp cât este vorba de un singur caracter.

print('left  : {:*<10}'.format(100))
print('center: {:a^10}'.format(100))
print('right : {:鬼>10}'.format(100))
# left  : 100*******
# center: aaa100aaaa
# right : 鬼鬼鬼鬼鬼鬼鬼100

Justificarea la dreapta cu > nu ia în considerare semnul (-,+). Dacă utilizați =, semnul este urmat de caracterul specificat. Dacă doriți să specificați +, scrieți + după =. Detaliile procesării semnelor sunt descrise ulterior.

print('sign: {:0>10}'.format(-100))
print('sign: {:0=10}'.format(-100))
print('sign: {:0=+10}'.format(100))
# sign: 000000-100
# sign: -000000100
# sign: +000000100

<, ^ și > pot fi specificate pentru șiruri de caractere, dar = va genera o eroare ValueError. Dacă doriți să utilizați = pentru un șir de caractere, trebuie să îl convertiți într-un număr folosind int().

# print('sign: {:0=10}'.format('-100'))
# ValueError: '=' alignment not allowed in string format specifier

print('sign: {:0=10}'.format(int('-100')))
# sign: -000000100

Același lucru este valabil și pentru numerele în virgulă mobilă. Punctele zecimale sunt, de asemenea, numărate ca un caracter.

print('left  : {:*<10}'.format(1.23))
print('center: {:a^10}'.format(1.23))
print('right : {:鬼>10}'.format(1.23))
# left  : 1.23******
# center: aaa1.23aaa
# right : 鬼鬼鬼鬼鬼鬼1.23

print('sign: {:0>10}'.format(-1.23))
print('sign: {:0=10}'.format(-1.23))
print('sign: {:0=+10}'.format(1.23))
# sign: 00000-1.23
# sign: -000001.23
# sign: +000001.23

Listele, tuplurile etc. vor cauza o eroare dacă sunt specificate ca atare și pot fi convertite în șiruri de caractere utilizând str().

l = [0, 1]
print(type(l))
# <class 'list'>

# print('{:*^16}'.format(l))
# TypeError: unsupported format string passed to list.__format__

print(type(str(l)))
# <class 'str'>

print('{:*^16}'.format(str(l)))
# *****[0, 1]*****

Pentru stânga-justificată, centru-justificată și dreapta-justificată, există, de asemenea, metode dedicate pentru șiruri de caractere numite ljust(), center() și rjust().

0 umplere

Dacă doriți să ajustați numărul de cifre prin umplerea cu zero, setați caracterul care urmează să fie umplut la 0 și corectați-l la dreapta.

În cazul umplerii cu zero, în cazul în care simbolul de aliniere este omis, acesta este prelucrat ca și cum ar fi fost specificat =.

print('zero padding: {:0=10}'.format(100))
print('zero padding: {:010}'.format(100))
# zero padding: 0000000100
# zero padding: 0000000100

print('zero padding: {:0=10}'.format(-100))
print('zero padding: {:010}'.format(-100))
# zero padding: -000000100
# zero padding: -000000100

=Dacă specificați un șir de caractere ca argument, așa cum este descris mai sus, veți primi o eroare. Să fim atenți.

# print('zero padding: {:010}'.format('-100'))
# ValueError: '=' alignment not allowed in string format specifier

Pentru completarea cu zero, există, de asemenea, o metodă dedicată pentru șiruri de caractere numită zfill().

Semn (plus sau minus)

În mod implicit, numai numerele negative sunt marcate cu un semn (minus-).

Atunci când se adaugă + la șirul de specificații de formatare, se afișează și un semn (plus +) pentru numerele pozitive. Dacă se adaugă un spațiu, se afișează un spațiu la începutul numărului pozitiv, iar numărul de cifre este aliniat cu cel al numărului negativ.

print('sign: {}'.format(100))
print('sign: {}'.format(-100))
# sign: 100
# sign: -100

print('sign: {:+}'.format(100))
print('sign: {:+}'.format(-100))
# sign: +100
# sign: -100

print('sign: {: }'.format(100))
print('sign: {: }'.format(-100))
# sign:  100
# sign: -100

Aveți grijă la completarea cu caractere arbitrare, cum ar fi completarea cu zero menționată mai sus. În mod implicit, fără + și fără spații, numerele pozitive se completează cu încă un caracter.

print('sign: {:06}'.format(100))
print('sign: {:06}'.format(-100))
# sign: 000100
# sign: -00100

print('sign: {:+06}'.format(100))
print('sign: {:+06}'.format(-100))
# sign: +00100
# sign: -00100

print('sign: {: 06}'.format(100))
print('sign: {: 06}'.format(-100))
# sign:  00100
# sign: -00100

În cazul în care se utilizează un simbol de aliniere, simbolul de desemnare a semnului trebuie scris după simbolul de aliniere.

print('sign: {:_>6}'.format(100))
print('sign: {:_>6}'.format(-100))
# sign: ___100
# sign: __-100

print('sign: {:_>+6}'.format(100))
print('sign: {:_>+6}'.format(-100))
# sign: __+100
# sign: __-100

print('sign: {:_> 6}'.format(100))
print('sign: {:_> 6}'.format(-100))
# sign: __ 100
# sign: __-100

Separator de cifre (virgulă, subliniere)

Adăugați o virgulă sau o subliniere _ ca separator la fiecare trei cifre. Acest lucru face ca numerele mari să fie mai ușor de citit. Rețineți că underscore_ este o opțiune adăugată în Python 3.6, deci nu poate fi utilizată în versiunile anterioare.

print('{:,}'.format(100000000))
# 100,000,000

print('{:_}'.format(100000000))
# 100_000_000

În cazul tipurilor de numere cu virgulă mobilă flotantă, se delimitează numai partea întreagă.

print('{:,}'.format(1234.56789))
# 1,234.56789

Numere binare, octale și hexazecimale

Convertește valorile numerice în numere binare, octale și hexazecimale pentru ieșire.

  • b: Binary
  • o: Octal
  • d: Decimal
  • x,X: Hexadecimal (literele majuscule sunt majuscule)
print('bin: {:b}'.format(255))
print('oct: {:o}'.format(255))
print('dec: {:d}'.format(255))
print('hex: {:x}'.format(255))
print('HEX: {:X}'.format(255))
# bin: 11111111
# oct: 377
# dec: 255
# hex: ff
# HEX: FF

De asemenea, poate fi combinat cu 0-fill și este adesea utilizat pentru a alinia cifrele în notația binară și hexazecimală.

print('bin: {:08b}'.format(255))
print('oct: {:08o}'.format(255))
print('dec: {:08d}'.format(255))
print('hex: {:08x}'.format(255))
print('HEX: {:08X}'.format(255))
# bin: 11111111
# oct: 00000377
# dec: 00000255
# hex: 000000ff
# HEX: 000000FF

Rețineți că numărul de caractere de umplere zero trebuie să fie specificat ținând cont de prefix.

print('bin: {:#010b}'.format(255))
print('oct: {:#010o}'.format(255))
print('dec: {:#010d}'.format(255))
print('hex: {:#010x}'.format(255))
print('HEX: {:#010X}'.format(255))
# bin: 0b11111111
# oct: 0o00000377
# dec: 0000000255
# hex: 0x000000ff
# HEX: 0X000000FF

În cazul numerelor binare și hexazecimale, se poate introduce doar separatorul de cifre _ (Python 3.6 sau o versiune ulterioară). Se utilizează un separator de 4 cifre; numărul de caractere completate cu zero trebuie să țină cont și de numărul de caractere de subliniere.

print('hex: {:08x}'.format(255))
print('hex: {:09_x}'.format(255))
print('hex: {:#011_x}'.format(255))
# hex: 000000ff
# hex: 0000_00ff
# hex: 0x0000_00ff

Numai tipul de număr întreg int poate converti formatul în binar sau hexazecimal. Puteți utiliza int() pentru a-l converti într-un număr.

# print('hex: {:08x}'.format('255'))
# ValueError: Unknown format code 'X' for object of type 'str'

print('hex: {:08x}'.format(int('255')))
# hex: 000000ff

Specificați numărul de cifre după punctul zecimal

Pentru a specifica numărul de cifre după virgulă, procedați după cum urmează: n este numărul de cifre. Numărul de cifre după virgulă devine numărul de cifre specificat, indiferent de numărul de cifre din partea întreagă.
.[n]f

print('{:.2f}'.format(123.456))
print('{:.5f}'.format(123.456))
print('{:.3f}'.format(0.0001234))
# 123.46
# 123.45600
# 0.000

Partea stângă a punctului zecimal poate fi specificată ca fiind justificată la stânga, justificată la centru, justificată la dreapta sau umplută cu zero, așa cum s-a descris mai sus. În cazul în care numărul de cifre ale valorii țintă este mai mare decât numărul specificat, nu se face nimic. Dacă numărul de cifre din valoarea țintă este mai mare decât numărul de cifre specificat, nu se face nimic.

print('{:>12.5f}'.format(123.456))
print('{:012.5f}'.format(123.456))
print('{:06.5f}'.format(123.456))
#    123.45600
# 000123.45600
# 123.45600

Dacă specificați un număr de cifre mai mic decât numărul inițial de cifre după virgulă, valoarea va fi rotunjită. Rețineți că nu se rotunjește la cel mai apropiat număr întreg, ci la un număr par, de exemplu, 0,5 este rotunjit la 0.

print('{:.0f}'.format(0.4))
print('{:.0f}'.format(0.5))
print('{:.0f}'.format(0.6))
# 0
# 0
# 1

Dacă doriți să utilizați rotunjirea generală, puteți utiliza metoda quantize() din biblioteca standard decimal.

notație exponențială

Atunci când un număr float în virgulă mobilă este convertit într-un șir de caractere, acesta va fi scris automat în notație exponențială în funcție de numărul de cifre. Tipul de număr întreg int nu face acest lucru.

print('{}'.format(0.0001234))
print('{}'.format(0.00001234))
# 0.0001234
# 1.234e-05

print('{}'.format(1234000000000000.0))
print('{}'.format(12340000000000000.0))
print('{}'.format(12340000000000000000000000))
# 1234000000000000.0
# 1.234e+16
# 12340000000000000000000000

Dacă specificați e sau E în șirul de specificații de formatare, puteți întotdeauna să faceți conversia în notație exponențială. Caracterele utilizate în ieșire vor fi e și, respectiv, E.

print('{:e}'.format(0.0001234))
print('{:E}'.format(0.0001234))
# 1.234000e-04
# 1.234000E-04

De asemenea, este posibil să se specifice numărul de cifre după virgulă. Partea întreagă va avea întotdeauna o cifră, iar punctul zecimal va avea numărul de cifre specificat.

print('{:.5e}'.format(0.0001234))
print('{:.2E}'.format(0.0001234))
# 1.23400e-04
# 1.23E-04

print('{:.5e}'.format(987.65))
print('{:.2E}'.format(987.65))
# 9.87650e+02
# 9.88E+02

Rețineți că, dacă specificați left-justified, center-justified, right-justified sau zero-filled, e-, E+ etc. vor fi, de asemenea, numărate ca cifre (caractere).

print('{:>12.5e}'.format(987.65))
print('{:012.2E}'.format(987.65))
#  9.87650e+02
# 00009.88E+02

Cifre semnificative (numărul de cifre semnificative)

Puteți specifica numărul total de cifre procedând după cum urmează În funcție de rezultat, se va utiliza automat notația exponențială. Rețineți că se vor omite zerourile din urmă după virgulă.
.[n]g

print('{:.2g}'.format(123.456))
print('{:.3g}'.format(123.456))
print('{:.8g}'.format(123.456))
print('{:.3g}'.format(0.0001234))
# 1.2e+02
# 123
# 123.456
# 0.000123

Dacă omiteți g, rezultatul nu va fi un număr întreg. g este același în majoritatea cazurilor, dar numai în cazurile în care rezultatul este un număr întreg.

print('{:.2}'.format(123.456))
print('{:.3}'.format(123.456))
print('{:.8}'.format(123.456))
print('{:.3}'.format(0.0001234))
# 1.2e+02
# 1.23e+02
# 123.456
# 0.000123

Dacă procesăm aceeași valoare, vom obține următoarele.

print('{:.3f}'.format(123.456))
print('{:.3e}'.format(123.456))
print('{:.3g}'.format(123.456))
print('{:.3}'.format(123.456))
# 123.456
# 1.235e+02
# 123
# 1.23e+02

print('{:.8f}'.format(123.456))
print('{:.8e}'.format(123.456))
print('{:.8g}'.format(123.456))
print('{:.8}'.format(123.456))
# 123.45600000
# 1.23456000e+02
# 123.456
# 123.456

În cazul lui g sau în cazul în care este omis, zerourile de după virgulă sunt omise, astfel încât, dacă doriți să afișați același număr de cifre semnificative (numărul de cifre semnificative), utilizați notația exponențială e sau E. Partea întreagă este întotdeauna o cifră, iar virgula zecimală este numărul specificat de cifre, astfel încât, dacă doriți să afișați n cifre semnificative, specificați doar n-1.

print('{:.4e}'.format(123.456))
print('{:.4e}'.format(0.000012345))
print('{:.4e}'.format(12))
# 1.2346e+02
# 1.2345e-05
# 1.2000e+01

Afișare procentuală

Dacă % este specificat în șirul de specificații de formatare, valoarea numerică float sau int este multiplicată cu 100 și convertită într-un șir de caractere cu %.

De asemenea, este posibil să se specifice numărul de cifre după virgulă. Valoarea implicită este de șase cifre după virgulă. De asemenea, sunt disponibile funcțiile Left-justify, center-justify, right-justify și zero-fill. % este, de asemenea, socotit ca un caracter.

print('{:%}'.format(0.12345))
print('{:.2%}'.format(0.12345))
# 12.345000%
# 12.35%

print('{:%}'.format(10))
print('{:.2%}'.format(10))
# 1000.000000%
# 1000.00%

print('{:>7.2%}'.format(0.12345))
print('{:07.2%}'.format(0.12345))
#  12.35%
# 012.35%