Es ist nützlich, um ungerade Spalten zu berücksichtigen, ohne dass man im Voraus wissen muss, wie viele Spalten man unterbringen kann:
>>> words = [string.ascii_lowercase] + list(string.ascii_lowercase)
>>> print format_list(words)
abcdefghijklmnopqrstuvwxyz b d f h j l n p r t v x z
a c e g i k m o q s u w y
Für Ihr Beispiel:
>>> foolist = ['exiv2-devel', 'mingw-libs', 'tcltk-demos', 'fcgi',
... 'netcdf', 'pdcurses-devel', 'msvcrt', 'gdal-grass', 'iconv',
... 'qgis-devel', 'qgis1.1', 'php_mapscript']
>>> print format_list(foolist, spacing=4, width=31)
exiv2-devel msvcrt
mingw-libs gdal-grass
tcltk-demos iconv
fcgi qgis-devel
netcdf qgis1.1
pdcurses-devel php_mapscript
Hier ist der Code. Beachten Sie, dass er auch Wörter mit ANSI-Farbcodes (z. B. aus dem colorama-Paket) verarbeitet - sie bringen die Spaltenbreiten nicht durcheinander.
ansi_pattern = re.compile(r'\x1b\[\d{1,2}m')
def get_nchars(string):
"""Return number of characters, omitting ANSI codes."""
return len(ansi_pattern.sub('', string))
def format_list(items, indent=0, spacing=2, width=79):
"""Return string listing items along columns.
items : sequence
List of items to display that must be directly convertible into
unicode strings. ANSI color codes may be present, and are taken
into account in determining column widths
indent : int
Number of spaces in left margin.
spacing : int
Number of spaces between columns.
width : int
Maximum number of characters per line, including indentation.
"""
if not items:
return u''
# Ensure all items are strings
items = [unicode(item) for item in items]
# Estimate number of columns based on shortest and longest items
minlen = min(get_nchars(item) for item in items)
maxlen = max(get_nchars(item) for item in items)
# Assume one column with longest width, remaining with shortest.
# Use negative numbers for ceiling division.
ncols = 1 - (-(width - indent - maxlen) // (spacing + min(1, minlen)))
ncols = max(1, min(len(items), ncols))
# Reduce number of columns until items fit (or only one column)
while ncols >= 1:
# Determine number of rows by ceiling division
nrows = -(-len(items) // ncols)
# Readjust to avoid empty last column
ncols = -(-len(items) // nrows)
# Split items into columns, and test width
columns = [items[i*nrows:(i+1)*nrows] for i in range(ncols)]
totalwidth = indent - spacing + sum(
spacing + max(get_nchars(item) for item in column)
for column in columns
)
# Stop if columns fit. Otherwise, reduce number of columns and
# try again.
if totalwidth <= width:
break
else:
ncols -= 1
# Pad all items to column width
for i, column in enumerate(columns):
colwidth = max(get_nchars(item) for item in column)
columns[i] = [
item + ' ' * (colwidth - get_nchars(item))
for item in column
]
# Transpose into rows, and return joined rows
rows = list(itertools.izip_longest(*columns, fillvalue=''))
return '\n'.join(
' ' * indent + (u' ' * spacing).join(row).rstrip()
for row in rows
)
1 Stimmen
Erstens ist es keine gute Idee, dict als Variablennamen zu verwenden. Zweitens ist das, was Sie hier zu drucken versuchen, eine Liste, ein dict verwendet {} und :, um die Schlüssel und Werte zu trennen
3 Stimmen
-1: Im Titel der Frage steht "Liste" - eine komplette Verdoppelung. In der Frage steht "dict". Der Beispielcode ist eine Liste - eine komplette Verdoppelung. Möchten Sie, dass die Liste in ein Diktat umgewandelt und ausgedruckt wird? Wenn ja, ändern Sie die Frage, um zu beschreiben, was Sie vraiment wollen.
0 Stimmen
Ich habe die Beschreibung und den Beispielcode wie empfohlen korrigiert. Der Titel und die Beschreibung spiegeln jetzt mein Ziel wider. Vielen Dank für die Korrekturen.
0 Stimmen
Wenn die Herabstufungen auf die anfängliche Verwirrung und die schlechte Formulierung zurückzuführen waren, nehmen Sie sie bitte zurück, da dies inzwischen behoben wurde. Wenn die Herabstufungen aus einem anderen Grund erfolgten, erklären Sie mir bitte, dass ich den Fehler beheben oder zumindest nicht noch einmal machen kann. Ich danke Ihnen.
0 Stimmen
Zu Downvotes: Downvoteure erhalten nach der Abstimmung keine Benachrichtigung über Kommentare :(
0 Stimmen
Re downvotes: Oh. Das ist bedauerlich. Ich kann die Logik, die zu dieser Funktion führt, nachvollziehen, aber es macht es Anfängern schwer, aus dem Loch herauszukommen. Danke für den Hinweis, sonst hätte ich weiterhin schlecht über S. Lott gedacht, weil er es ignoriert hat.
1 Stimmen
Im Jahr 2021 empfehle ich Ihnen, die Antworten von Claudio y Epischer Wink für ihre Verwendung von
columnize
.0 Stimmen
Danke @CameronSmith. Epic Wink's ist direkt und kurz genug, um die akzeptierte Antwort zu ändern, für py3.