Wie drucke ich eine Zeichenfolge in fester Breite?


103

Ich habe diesen Code (Drucken des Auftretens aller Permutationen in einer Zeichenfolge)

def splitter(str):
    for i in range(1, len(str)):
        start = str[0:i]
        end = str[i:]
        yield (start, end)
        for split in splitter(end):
            result = [start]
            result.extend(split)
            yield result    

el =[];

string = "abcd"
for b in splitter("abcd"):
    el.extend(b);

unique =  sorted(set(el));

for prefix in unique:
    if prefix != "":
        print "value  " , prefix  , "- num of occurrences =   " , string.count(str(prefix));

Ich möchte das gesamte Permutationsvorkommen drucken, das in einer variablen Zeichenfolge vorhanden ist.

Da die Permutation nicht die gleiche Länge hat, möchte ich die Breite korrigieren und in einer schönen Form drucken, die nicht so ist:

value   a - num of occurrences =    1
value   ab - num of occurrences =    1
value   abc - num of occurrences =    1
value   b - num of occurrences =    1
value   bc - num of occurrences =    1
value   bcd - num of occurrences =    1
value   c - num of occurrences =    1
value   cd - num of occurrences =    1
value   d - num of occurrences =    1

Wie kann ich formatdas machen?

Ich habe diese Beiträge gefunden, aber es passte nicht gut zu alphanumerischen Zeichenfolgen:

Python-String-Formatierung feste Breite

Feste Länge mit Python einstellen


1
Was ist mit Print '% 10s'% 'Mystring'
TJD

2
Überrascht, dass dies "\t"in keiner Lösung als Option aufgeführt ist.

Antworten:


112

EDIT 2013-12-11 - Diese Antwort ist sehr alt. Es ist immer noch gültig und korrekt, aber Leute, die sich das ansehen, sollten die neue Formatsyntax bevorzugen .

Sie können die Zeichenfolgenformatierung wie folgt verwenden:

>>> print '%5s' % 'aa'
   aa
>>> print '%5s' % 'aaa'
  aaa
>>> print '%5s' % 'aaaa'
 aaaa
>>> print '%5s' % 'aaaaa'
aaaaa

Grundsätzlich:

  • Der %Charakter informiert Python, dass er einen Token durch etwas ersetzen muss
  • Das sZeichen informiert Python, dass das Token eine Zeichenfolge sein wird
  • Die 5(oder eine beliebige Zahl) weist Python an, die Zeichenfolge mit Leerzeichen von bis zu 5 Zeichen aufzufüllen.

In Ihrem speziellen Fall könnte eine mögliche Implementierung folgendermaßen aussehen:

>>> dict_ = {'a': 1, 'ab': 1, 'abc': 1}
>>> for item in dict_.items():
...     print 'value %3s - num of occurances = %d' % item # %d is the token of integers
... 
value   a - num of occurances = 1
value  ab - num of occurances = 1
value abc - num of occurances = 1

SEITLICHER HINWEIS: Ich habe mich nur gefragt, ob Ihnen die Existenz des itertoolsModuls bekannt ist . Zum Beispiel könnten Sie eine Liste aller Ihrer Kombinationen in einer Zeile erhalten mit:

>>> [''.join(perm) for i in range(1, len(s)) for perm in it.permutations(s, i)]
['a', 'b', 'c', 'd', 'ab', 'ac', 'ad', 'ba', 'bc', 'bd', 'ca', 'cb', 'cd', 'da', 'db', 'dc', 'abc', 'abd', 'acb', 'acd', 'adb', 'adc', 'bac', 'bad', 'bca', 'bcd', 'bda', 'bdc', 'cab', 'cad', 'cba', 'cbd', 'cda', 'cdb', 'dab', 'dac', 'dba', 'dbc', 'dca', 'dcb']

und Sie könnten die Anzahl der Vorkommen erhalten, indem Sie combinationsin Verbindung mit verwenden count().


24
Sie sollten vielleicht erwähnen, dass negative Zahlen eine linksbündige, gepolsterte Ausgabe ergeben. Dies ist für einen Anfänger kaum intuitiv.
Tripleee

+1 für @tripleee, ohne deine negativen Zahlen gib einen linksbündigen Kommentar ab. Ich hätte meinen Kopf länger geschlagen ... thx m8.
Briford Wylie

Dies ist weitaus intuitiver und prägnanter als das neue str.format. Ich verstehe nicht, warum es diesen Schub in Python in Richtung Faltung gibt
Scottmrogowski

Gibt es eine Möglichkeit, die Leerzeichen mit einem bestimmten Zeichen auszufüllen? Zum Beispiel, wenn wir "05" anstelle von "5"
drucken müssen

1
Hier sind einige weitere Tricks für den eleganten Druck mit fester Breite und F-Strings auf Medium .
Pfabri

197

Ich finde die Verwendung str.formatviel eleganter:

>>> '{0: <5}'.format('ss')
'ss   '
>>> '{0: <5}'.format('sss')
'sss  '
>>> '{0: <5}'.format('ssss')
'ssss '
>>> '{0: <5}'.format('sssss')
'sssss'

Wenn Sie die Zeichenfolge richtig ausrichten möchten, verwenden Sie >anstelle von <:

>>> '{0: >5}'.format('ss')
'   ss'

Bearbeiten: Wie in den Kommentaren erwähnt: Die 0 gibt den Index des Arguments an, an das übergeben wurde str.format().


5
Darüber hinaus gibt die 0 die Position des Formatarguments an, sodass Sie zwei weitere Aktionen ausführen können : '{<5}'.format('ss') 'ss 'Wie zuvor, jedoch ohne die 0, 'Second {1: <5} and first {0: <5}'.format('ss', 'sss') 'Second sss and first ss 'können Sie dieselbe Variable mehrmals in einer einzelnen Ausgabe neu anordnen oder sogar ausgeben Zeichenfolge.
Mightypile

14
Ich kann den vorherigen Kommentar, der ihn benötigt, nicht mehr bearbeiten. {<5}funktioniert nicht, aber {: <5}ohne den Indexwert.
Mightypile

9
Hier ist die Mini-Sprache für die Python -Formatspezifikation , die diese Formatzeichenfolgen und zusätzliche Optionen beschreibt. Zur schnellen Bezugnahme ist der Raum in {0: <5}der [fill] , der <ist [align]und 5ist[width]
cod3monk3y

2
Diese 5 kann eine variable Substitution sein>>> print width 20 >>> print "{0: <{width}}".format("ssssss", width=width).split('\n') ['ssssss '] >>>
user2763554

4
Sie können auch Zahlen verwenden und die Variablen der Reihe nach auflisten width=10; "{0: <{1}}".format('sss', width). Oder lassen Sie sogar die Zahlen '{: <{}}'.format('sss', width)
weg

71

Ursprünglich als Bearbeitung der Antwort von @ 0x90 veröffentlicht, wurde sie jedoch abgelehnt, weil sie von der ursprünglichen Absicht des Beitrags abwich, und empfohlen, sie als Kommentar oder Antwort zu veröffentlichen. Daher füge ich hier die kurze Beschreibung hinzu.

Zusätzlich zur Antwort von @ 0x90 kann die Syntax flexibler gestaltet werden, indem eine Variable für die Breite verwendet wird (gemäß dem Kommentar von @ user2763554):

width=10
'{0: <{width}}'.format('sss', width=width)

Außerdem können Sie diesen Ausdruck kürzer machen, indem Sie nur Zahlen verwenden und sich auf die Reihenfolge der Argumente verlassen, die an Folgendes übergeben werden format:

width=10
'{0: <{1}}'.format('sss', width)

Oder lassen Sie sogar alle Zahlen für maximale, möglicherweise nicht pythonisch implizite Kompaktheit weg:

width=10
'{: <{}}'.format('sss', width)

Update 2017-05-26

Mit der Einführung formatierter String-Literale (kurz "f-Strings") in Python 3.6 ist es jetzt möglich, auf zuvor definierte Variablen mit einer kürzeren Syntax zuzugreifen:

>>> name = "Fred"
>>> f"He said his name is {name}."
'He said his name is Fred.'

Dies gilt auch für die Formatierung von Zeichenfolgen

>>> width=10
>>> string = 'sss'
>>> f'{string: <{width}}'
'sss       '

Diese Antwort gefällt mir sehr gut!
Syrtis Major

10

formatist definitiv der eleganteste Weg, aber afaik kann man das nicht mit dem Python- loggingModul verwenden, also hier ist, wie man es mit der %Formatierung machen kann:

formatter = logging.Formatter(
    fmt='%(asctime)s | %(name)-20s | %(levelname)-10s | %(message)s',
)

Hier zeigt das -die linke Ausrichtung an, und die Zahl davor sgibt die feste Breite an.

Einige Beispielausgaben:

2017-03-14 14:43:42,581 | this-app             | INFO       | running main
2017-03-14 14:43:42,581 | this-app.aux         | DEBUG      | 5 is an int!
2017-03-14 14:43:42,581 | this-app.aux         | INFO       | hello
2017-03-14 14:43:42,581 | this-app             | ERROR      | failed running main

Weitere Informationen finden Sie in den Dokumenten hier: https://docs.python.org/2/library/stdtypes.html#string-formatting-operations


Dies verkürzt jedoch keine Zeichenfolgen über 20 Zeichen. Verwenden Sie '%(name)20.20s'die 20 als minimale und maximale Saitenlänge!
xjcl

Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.