954,515 Members — Technology Publication meets Social Media
Username:
Password:
Lost login information?
Have something to say? Contribute New Article Reply to this Article

Simple formatting question

Hey guys,

This is a quick formatting question that I'm having trouble with. I'm trying to create columns of numbers, but I want the columns to only be as large as the largest number in that column. I was trying to use format() width, but that is creating a width between the numbers so the columns don't line up. What I want is something that looks like this (where each of the numbers are a different variable):

CARD  1   5   3   1
CARD 10  23   3  23
CARD  1 122   3 233

Hopefully that makes sense. This problem seems like an easy fix but I can't figure it out and its really bothering me!

Thanks in advance.

fatalaccidents
Newbie Poster
23 posts since Feb 2011
Reputation Points: 10
Solved Threads: 0
 

You would first have to store the rows so you can find the largest number in each column. Post the code for that and we would then have enough info to be able to help with the final formatting.

woooee
Nearly a Posting Maven
2,454 posts since Dec 2006
Reputation Points: 777
Solved Threads: 714
 

Hey, I actually already have that part. Here is what I had so far (as far as getting the largest a number would take up in a row).

76 mw_facets = 1 + int(len(str(num_facets)))
 77 max_tot = 1 + max(len(item) for item in Cells)
 78 max_mat = 1 + max(len(item) for item in Mats)
 79 max_node = 1 + int(len(str(num_nodes)))
 80 max_sp_node = 1 + int(len(str(Nodes[0])))
 81 
 82 padding = ' '
 83 num_facets = int(num_facets)
 84 
 85 f2.write("MESH3D\n")
 86 for i in range(0,num_facets):
 87    E_cnt =  '{0}{p:{mw_facets}}{count}'.format('E4T', p=padding, mw_facets=mw_facets, count=count)
 88    C_cnt = '{p:{r}}{Cell1}{p:{r}}{Cell2}{p:{r}}{Cell3}{p:{r}}{Cell4}{p:{r}}'.format(p=padding, r=max_tot,
 89             Cell1 = Cells[i][0], Cell2 = Cells[i][1], Cell3 = Cells[i][2], Cell4 = Cells[i][3])
 90    M_cnt = '{p:{r}}{Mat}'.format(p=padding, r=max_mat, Mat=Mats[i])
 91    TDM_line = E_cnt + C_cnt + M_cnt
 92    f2.write(TDM_line+'\n')
 93    count += 1


I'm really new to python so any simple suggestions to make my code less ... ugly would also be appreciated. The problem with this code right now is that it takes that maximum space a number will take up and puts that amount between rows. I want the numbers to line up and at least have one space (when the number is the largest) between them, but always the same amount of space between them. I hope I'm being clear, and if I'm not just let me know how I can explain better. Thanks for the reply!

fatalaccidents
Newbie Poster
23 posts since Feb 2011
Reputation Points: 10
Solved Threads: 0
 

You can compute the column widths and then generate a template for the format() method:

cells = [
    [ 1, 5, 3, 1],
    [ 10, 23, 3, 23 ],
    [ 1, 122, 3, 233]
]

scells = [[str(x) for x in line] for line in cells]
columns = zip(*scells)
padding = 2
width = [ max(len(s) for s in col) for col in columns ]
template = ''.join(["{{{0}:>{1}d}}".format(i, w+padding) for i, w in enumerate(width)])
print "cells:", cells
print "scells:", scells
print "columns:", columns
print "width:", width
print "template:", template

for line in cells:
    print template.format(*line)
    
""" my output -->
cells: [[1, 5, 3, 1], [10, 23, 3, 23], [1, 122, 3, 233]]
scells: [['1', '5', '3', '1'], ['10', '23', '3', '23'], ['1', '122', '3', '233']]
columns: [('1', '10', '1'), ('5', '23', '122'), ('3', '3', '3'), ('1', '23', '233')]
width: [2, 3, 1, 3]
template: {0:>4d}{1:>5d}{2:>3d}{3:>5d}
   1    5  3    1
  10   23  3   23
   1  122  3  233
"""
Gribouillis
Posting Maven
Moderator
2,786 posts since Jul 2008
Reputation Points: 1,044
Solved Threads: 691
 

In that case it is pretty simple. You can just the format string % operator, see 5.6.2. String Formatting Operations . An example, and it looks like you've already padded by one space so I don't.

lens_list = [5, 3, 10]
data_list = [ [123, 17, 12345], [12, 18, 123456789], [2345, 1, 2]]

format_str = "Card"
for length in lens_list:
    format_str += "%"+str(length)+"d"
print format_str ## for your info

for data in data_list:
    print format_str % (data[0], data[1], data[2])
woooee
Nearly a Posting Maven
2,454 posts since Dec 2006
Reputation Points: 777
Solved Threads: 714
 

Thank you both for your replies. I haven't tried either of them out, but I'm sure I'll be able to work it out from the information you've given me. Greatly appreciated!

fatalaccidents
Newbie Poster
23 posts since Feb 2011
Reputation Points: 10
Solved Threads: 0
 

This article has been dead for over three months

Post: Markdown Syntax: Formatting Help
You
View similar articles that have also been tagged: