ฉันจะเติมสตริง Python ด้วยช่องว่างได้อย่างไร


509

ฉันต้องการกรอกสตริงด้วยช่องว่าง ฉันรู้ว่างานต่อไปนี้เป็นศูนย์

>>> print  "'%06d'"%4
'000004'

แต่ฉันควรทำอย่างไรเมื่อฉันต้องการสิ่งนี้:

'hi    '

แน่นอนฉันสามารถวัดความยาวสตริงและทำstr+" "*leftoverแต่ฉันต้องการวิธีที่สั้นที่สุด


1
ฉันรู้ว่ามันอาจเลิกใช้แล้วในอนาคต แต่ฉันก็ยังชอบวิธีการแบบเดิมที่ดีนี้: "%-6s" % sสำหรับการจัดชิดซ้ายและการจัดชิด"%6s" % sขวา
Basj

คำตอบ:


700

คุณสามารถทำได้ด้วยstr.ljust(width[, fillchar]):

กลับสตริงซ้ายธรรมในสายของความยาวความกว้าง การเติมเต็มทำได้โดยใช้fillchar ที่ระบุ(ค่าดีฟอลต์คือช่องว่าง) สตริงเดิมถูกส่งกลับถ้าความกว้างlen(s)น้อยกว่า

>>> 'hi'.ljust(10)
'hi        '

18
คำตอบของ @simon มีความยืดหยุ่นและมีประโยชน์มากขึ้นเมื่อทำการจัดรูปแบบสตริงที่ซับซ้อนมากขึ้น
CoatedMoose

3
หรือ @abbot 's หากคุณติดสนับสนุน python รุ่นเก่า
CoatedMoose

1
ljust () เลิกใช้แล้ว ดูstackoverflow.com/questions/14776788/…เพื่อดูวิธีการที่ถูกต้อง
Mawg กล่าวว่าการคืนสถานะโมนิก้า

มันหายไปในหลาม 3? เพียงแค่ต้องการเพิ่มนั่นก็คือ rjust และ center ซึ่งทำงานในลักษณะเดียวกัน แต่สำหรับการจัดแนวที่ต่างกัน
radtek

17
ljust (), rjust () ได้รับการคัดค้านจากโมดูลสตริงเท่านั้น พวกเขามีอยู่ในประเภท str builtin
Rohan Grover

373

สำหรับวิธีการที่ยืดหยุ่นที่ใช้งานได้แม้ในการจัดรูปแบบสตริงที่ซับซ้อนคุณอาจใช้การจัดรูปแบบสตริงขนาดเล็กโดยใช้วิธีใดstr.format()วิธีหนึ่ง

>>> '{0: <16} StackOverflow!'.format('Hi')  # Python >=2.6
'Hi               StackOverflow!'

ของf- สตริง

>>> f'{"Hi": <16} StackOverflow!'  # Python >= 3.6
'Hi               StackOverflow!'

11
ถ้าคุณมี '16' ในตัวแปรล่ะ
แรนดี้

ฉันก็รู้เรื่องนั้นเช่นกัน ควรมีการโพสต์มัน เอกสารกล่าวว่าสิ่งนี้ควรใช้กับ Py2.6 แต่การค้นพบของฉันเป็นอย่างอื่น ทำงานใน Py2.7 ได้
แรนดี้

1
ฉันมีปัญหากับการจัดรูปแบบประเภทนี้เมื่อฉันใช้สำเนียงระดับชาติ คุณต้องการให้ 'kra' และ 'krá' เหมือนกัน แต่ไม่ใช่
quapka

77
@Randy'{message: <{fill}}'.format(message='Hi', fill='16')
CivFan

19
อย่าใช้str.format()สำหรับเทมเพลตที่มีเพียงอันเดียว{...}และไม่มีอะไรอื่น เพียงแค่ใช้ฟังก์ชั่นและบันทึกตัวเองแยกค่าใช้จ่าย:format() format('Hi', '<16')
Martijn Pieters

119

วิธีการจัดรูปแบบสตริงใหม่ (ish) ช่วยให้คุณทำเรื่องสนุก ๆ ด้วยอาร์กิวเมนต์คำหลักที่ซ้อนกัน กรณีที่ง่ายที่สุด:

>>> '{message: <16}'.format(message='Hi')
'Hi             '

หากคุณต้องการส่งผ่าน16เป็นตัวแปร:

>>> '{message: <{width}}'.format(message='Hi', width=16)
'Hi              '

หากคุณต้องการส่งผ่านตัวแปรสำหรับชุดและ kaboodle ทั้งหมด :

'{message:{fill}{align}{width}}'.format(
   message='Hi',
   fill=' ',
   align='<',
   width=16,
)

ผลลัพธ์ใด (คุณเดาได้):

'Hi              '

คุณจะจัดการกับข้อความที่แตกต่างกันอย่างไร msgs = ['hi', 'hello', 'ciao']
ak_slick

1
@ak_slick คุณสามารถส่งผ่านตัวแปรแทนค่าฮาร์ดโค้ดลงในฟังก์ชันการจัดรูปแบบ
CivFan

80

คุณสามารถลองสิ่งนี้:

print "'%-100s'" % 'hi'

พิมพ์ "'% -6s'"% 'สวัสดี' แน่นอน !!
เรียว

8
@simon เป็นคนที่ติดอยู่กับระบบ python2.5 คำตอบนี้ช่วยฉันได้ไม่ใช่คำตอบที่ไร้ประโยชน์ +1
sunshinekitty

18
ไม่เลิกใช้แล้วใน 3.3+
Seppo Erviälä

3
ฉันชอบไวยากรณ์ printf ทั่วไปนี้ดีกว่ามาก ช่วยให้คุณเขียนสตริงที่ซับซ้อนโดยไม่มีการต่อข้อมูลนับไม่ถ้วน
Max Tsepkov

4
เพื่อความสมบูรณ์"'%+100s'" % 'hi'จะใช้เพื่อวางช่องว่างทางด้านขวาของ'hi'
Eric Blum

62

วิธีที่ถูกต้องในการทำเช่นนี้คือการใช้รูปแบบไวยากรณ์ของงูใหญ่ตามที่อธิบายไว้ในเอกสารประกอบอย่างเป็นทางการ

สำหรับกรณีนี้มันจะเป็นเพียงแค่:
'{:10}'.format('hi')
ผลลัพธ์ที่:
'hi '

คำอธิบาย:

format_spec ::=  [[fill]align][sign][#][0][width][,][.precision][type]
fill        ::=  <any character>
align       ::=  "<" | ">" | "=" | "^"
sign        ::=  "+" | "-" | " "
width       ::=  integer
precision   ::=  integer
type        ::=  "b" | "c" | "d" | "e" | "E" | "f" | "F" | "g" | "G" | "n" | "o" | "s" | "x" | "X" | "%"

ค่อนข้างทุกสิ่งที่คุณต้องรู้มี ^.

Update: ตั้งแต่ python 3.6 สะดวกยิ่งขึ้นด้วยการแก้ไขสตริงตามตัวอักษร!

foo = 'foobar'
print(f'{foo:10} is great!')
# foobar     is great!

37

การใช้str.ljust():

>>> 'Hi'.ljust(6)
'Hi    '

นอกจากนี้คุณยังควรพิจารณาstring.zfill(), str.ljust()และstr.center()สำหรับการจัดรูปแบบสตริง สิ่งเหล่านี้สามารถถูกล่ามโซ่และมีการระบุอักขระ ' เติม ' ดังนี้

>>> ('3'.zfill(8) + 'blind'.rjust(8) + 'mice'.ljust(8, '.')).center(40)
'        00000003   blindmice....        '

การดำเนินการจัดรูปแบบสตริงเหล่านี้มีข้อดีของการทำงานใน Python v2 และ v3

ลองดูpydoc strบางครั้ง: มีสิ่งดีๆมากมายอยู่ในนั้น


27

จาก Python 3.6 คุณสามารถทำได้

>>> strng = 'hi'
>>> f'{strng: <10}'

กับการแก้ไขสตริงตัวอักษร

หรือหากขนาดการเติมเต็มของคุณอยู่ในตัวแปรเช่นนี้ (ขอบคุณ @Matt M. !):

>>> to_pad = 10
>>> f'{strng: <{to_pad}}'

4
f'{strng: >10}'สำหรับการเติมสตริงด้วยช่องว่างนำไปสู่ความยาว 10 นั่นคือเวทย์มนตร์ และมันก็ไม่ได้บันทึกไว้อย่างดี
Chang Ye

@changye f'{strng:10}'ผมเชื่อว่านี่ยังเป็นพฤติกรรมที่เริ่มต้นของ
WAF


7

ใช้การจัดรูปแบบมินิของ Python 2.7 สำหรับสตริง :

'{0: <8}'.format('123')

สิ่งนี้จัดชิดซ้ายและวางได้ถึง 8 อักขระด้วยอักขระ ''


4
@simon ได้ให้คำตอบนี้แล้ว ... ทำไมโพสต์คำตอบที่ซ้ำกัน?
เฟลิกซ์ลิ่ง

5
ฉันไม่ได้คลิก 'ตอบกลับใหม่โพสต์คลิกเพื่อรีเฟรช' และพลาดไปเลย
aodj


2

การใช้ตัวแบ่งส่วนข้อมูลจะเป็นแบบ pythonic มากกว่านี้หรือไม่

ตัวอย่างเช่นหากต้องการรองสตริงด้วยช่องว่างทางด้านขวาจนกระทั่งมีความยาว 10 อักขระ:

>>> x = "string"    
>>> (x + " " * 10)[:10]   
'string    '

หากต้องการรองด้วยช่องว่างทางด้านซ้ายจนกระทั่งมีความยาว 15 อักขระ:

>>> (" " * 15 + x)[-15:]
'         string'

แน่นอนว่าคุณต้องรู้ระยะเวลาที่คุณต้องการแพด แต่ไม่จำเป็นต้องวัดความยาวของสตริงที่คุณเริ่มต้นด้วย


9
ไม่มันจะไม่
นักฟิสิกส์บ้า

1
คุณอธิบายรายละเอียดเกี่ยวกับเรื่องนั้นได้ไหม? ไม่ใช่ว่าฉันไม่เชื่อคุณฉันแค่อยากจะเข้าใจว่าทำไม
Zev Chonoles

4
แน่ใจ วิธี pythonic ที่มากที่สุดคือการใช้หนึ่งในฟังก์ชั่น builtin แทนที่จะใช้วิธีการแก้ปัญหาพื้นบ้านให้มากที่สุด
นักฟิสิกส์บ้า

@MadPhysicist ที่บอกว่าการแบ่งเป็น pythonic น้อยกว่าเพราะคุณควรใช้ในฟังก์ชั่นที่สร้างขึ้นเหมือนกับการพูดว่า''.join(reversed(str))เป็น pythonic มากกว่าstr[::-1]และเราทุกคนรู้ว่ามันไม่เป็นความจริง
นิค

@NickA นั่นไม่ใช่การเปรียบเทียบที่ดีมาก กรณีที่คุณใช้เป็นตัวอย่างค่อนข้างถูกต้อง แต่อยู่ในความคิดของฉันมากขึ้นซับซ้อนกว่าการใช้(x + " " * 10)[:10] x.ljust(10)
นักฟิสิกส์บ้า

0

เคล็ดลับที่ดีที่จะใช้แทนรูปแบบการพิมพ์ต่างๆ:

(1) แผ่นที่มีช่องว่างทางด้านขวา:

('hi' + '        ')[:8]

(2) แผ่นที่มีศูนย์นำหน้าทางซ้าย:

('0000' + str(2))[-4:]

1
ด้วยเหตุผลบางอย่างนี่เป็นคำตอบที่สนุกที่สุด แต่ฉันชอบ ตามแนวเหล่านั้นให้พิจารณาด้วย min_len = 8ถ้าอย่างนั้น('hi' + ' '*min_len)[:min_len]หรือ('0'*min_len + str(2))[-min_len]
Poikilos

1
สำหรับตัวเลขมันจะ('0'*min_len + str(2))[-min_len:]ค่อนข้างแม้ว่าจะเป็นเพียงเพื่อความสนุกสนานและฉันขอแนะนำคำตอบอื่น ๆ
Poikilos

-1

คุณสามารถทำได้โดยใช้ list comprehension นี่จะทำให้คุณมีความคิดเกี่ยวกับจำนวนของช่องว่างเช่นกันและจะเป็นหนึ่งซับ

"hello" + " ".join([" " for x in range(1,10)])
output --> 'hello                 '

... แล้วคุณจะได้รับสตริงที่ 22 (len ( "สวัสดี") + 17 :() ตัวละครยาว - ที่ไม่ได้เป็นไปด้วยดีในขณะที่เรากำลังเป็นตลกที่เราสามารถทำได้. s = "hi"; s + (6-len(s)) * " "แทน (มันก็โอเคเมื่อ ผลลัพธ์จะเป็นค่าลบ) อย่างไรก็ตามคำตอบที่ใช้คุณลักษณะเฟรมเวิร์กที่แก้ไขปัญหาที่แน่นอนจะง่ายต่อการดูแลรักษา (ดูคำตอบอื่น ๆ )
Poikilos
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.