如何计算多个数字的位数,然后以表格形式对它们进行格式化?

时间:2017-09-01 09:42:35

标签: python string string-formatting

我有一个非常简单的程序,我正在为课堂写作,根据固定的票价来计算收入。在将其乘以用户提供的多张票之后,首先使用逗号在数千个位置对其进行格式化,然后在其前面添加一个美元符号,最后将其作为字符串返回,以便在列中列出固定标题在顶部。

我想知道的是,是否有办法首先计算结尾处生成的字符串中的位数(包括美元符号和逗号),并根据该数字调整列的宽度如果这有意义,则空格比正确显示列标题的最小空格数长。

就像一个FYI一样,脚本已经按照项目的要求输出结果,我只是想进一步扩展自己的理解。另外,我知道这可能不是构建这个程序的最佳方式,所以欢迎任何建议:

# Define ticket prices

SILVER_TIC_PRICE = 35
GOLD_TIC_PRICE = 55
PLATINUM_TIC_PRICE = 85

# Create Functions

# Validate tickets sold as an interger

def tickets_sold(message):
    while True:
        try:
            user_input = int(input(message))
        except ValueError:
            print('\nERROR : \nInvalid entry \nPlease use a number\n')
            continue
        try:
            assert user_input >= 0
        except AssertionError:
            print('\nERROR : \nInvalid entry \nPlease use a positive number\n')
            continue
        else:
            return user_input
            break

# Reusable line function

def print_line(ticket_class, tickets_sold, ticket_revenue):
    print(format(ticket_class, " >8"), format(tickets_sold, " >7"), format(ticket_revenue, " <7"), sep='  ')

# Format Function

# def format_final()

# Get the number of tickets sold by type
# But first a blank line for readability

print(' ')

# Get Silver tickets sold

silver_tickets_sold = tickets_sold ('Enter the number of Silver tickets sold: ')

# Get Gold tickets sold

gold_ticket_sold = tickets_sold('Enter the number of Gold tickets sold: ')

# Get Platinum tickets sold

platinum_ticket_sold = tickets_sold('Enter the number of Platinum tickets sold: ')

# calculate revenue

silver_initial = int(silver_tickets_sold * SILVER_TIC_PRICE)
gold_initial = int(gold_ticket_sold * GOLD_TIC_PRICE)
platinum_initial = int(platinum_ticket_sold * PLATINUM_TIC_PRICE)

silver_final = "{:,}".format(silver_initial)
gold_final = "{:,}".format(gold_initial)
platinum_final = "{:,}".format(platinum_initial)

silver_revenue = '$' + str(silver_final)
gold_revenue = '$' + str(gold_final)
platinum_revenue = '$' + str(platinum_final)

# calculate totals

total_tickets = int(silver_tickets_sold + gold_ticket_sold + platinum_ticket_sold)
total_initial = int(silver_initial + gold_initial + platinum_initial)

total_final = "{:,}".format(total_initial)

total_revenue = '$'+str(total_final)

# display results

print(' ')
print_line('Section','Tickets','Revenue')
print_line('--------','-------','-------')
print_line('Silver', silver_tickets_sold, silver_revenue)
print_line('Gold', gold_ticket_sold,gold_revenue)
print_line('Platinum', platinum_ticket_sold, platinum_revenue)
print_line('========','=======','=======')
print_line('Total', total_tickets, total_revenue)
print(' ')

我知道已有问题可以回答部分内容,但我无法找到任何能够以我能够包裹大脑的方式组合各个部分的内容。

3 个答案:

答案 0 :(得分:0)

如果数字和你只对数量感兴趣,那么它就是基数十。

import math
math.ceil(math.log(n,10))

应该有效。 或者您可以使用以下任何一种:

len(str(n))

len(str(n).replace(".",""))

答案 1 :(得分:0)

我已经汇总了一个小代码,它将为您提供最终字符串total_revenue中的数字数。

# Initialize the counter
count_number = 0

# Get the count of numbers
for c in total_revenue:
    if(c.isdigit()):
        count_number += 1

# Display the count
print(count_number)

答案 2 :(得分:0)

好的,让我先从一些代码审查开始:

第一个功能非常好。它正确使用while Truebreak,直到给出有效数字。但是还有一些改进的空间:

def tickets_sold(message):
    while True:
        try:
            user_input = int(input(message))
        except ValueError:
            print('\nERROR : \nInvalid entry \nPlease use a number\n')
            continue
        if user_input < 0:   # better to use an if instead of "try: assert"
            print('\nERROR : \nInvalid entry \nPlease use a positive number\n')
            continue
        return user_input  # just return all other cases already "continue"d

然而,它开始时会重复很多次,我会把代码请求票证,然后返回票证数量和收入。通过将其中的一部分放入函数中,可以简单地避免重复(不是全部)重复:

def get_tickets_and_revenue(name, tic_price):
    n_tickets_sold = tickets_sold('Enter the number of {} tickets sold: '.format(name))
    revenue = int(n_tickets_sold * tic_price)
    return n_tickets_sold, revenue


silver_tickets_sold, silver_revenue = get_tickets_and_revenue('Silver', SILVER_TIC_PRICE)
gold_ticket_sold, gold_revenue = get_tickets_and_revenue('Gold', GOLD_TIC_PRICE)
platinum_ticket_sold, platinum_revenue = get_tickets_and_revenue('Platinum', PLATINUM_TIC_PRICE)

total_tickets = silver_tickets_sold + gold_ticket_sold + platinum_ticket_sold
total_revenue = silver_revenue + gold_revenue + platinum_revenue

def format_number_according_to_spec(num):
    return '${:,}'.format(num)

# only now convert them to strings!
silver_revenue = format_number_according_to_spec(silver_revenue)
gold_revenue = format_number_according_to_spec(gold_revenue)
platinum_revenue = format_number_according_to_spec(platinum_revenue)
total_revenue = format_number_according_to_spec(total_revenue)

下一部分可能会通过将值保持为可迭代来缩短,但它也适用于硬编码:

def find_column_length(*column_values):
    # using "len(str(sth))" you can determine the length!
    return max(len(str(value)) for value in column_values)

# The row formatter is formatted twice, once with the length values and once
# with the actual values. So we need to escape the outer {} by doubling them.
row_formatter = '{{:>{}}}  {{:>{}}}  {{:>{}}}'
column_lengths = [find_column_length('Section', 
                                     'Silver', 
                                     'Gold', 
                                     'Platinum', 
                                     'Total'),
                  find_column_length('Tickets', 
                                     silver_tickets_sold, 
                                     gold_ticket_sold, 
                                     platinum_ticket_sold, 
                                     total_tickets),
                  find_column_length('Revenue', 
                                     silver_revenue, 
                                     gold_revenue, 
                                     platinum_revenue, 
                                     total_revenue)]
row_formatter = row_formatter.format(*column_lengths)
placeholder1 = '{}  {}  {}'.format('-'*column_lengths[0],
                                   '-'*column_lengths[1],
                                   '-'*column_lengths[2])
placeholder2 = '{}  {}  {}'.format('='*column_lengths[0],
                                   '='*column_lengths[1],
                                   '='*column_lengths[2])

print(' ')
print(row_formatter.format('Section','Tickets','Revenue'))
print(placeholder1)
print(row_formatter.format('Silver', silver_tickets_sold, silver_revenue))
print(row_formatter.format('Gold', gold_ticket_sold,gold_revenue))
print(row_formatter.format('Platinum', platinum_ticket_sold, platinum_revenue))
print(placeholder2)
print(row_formatter.format('Total', total_tickets, total_revenue))
print(' ')

例如:

Enter the number of Silver tickets sold: 200000000
Enter the number of Gold tickets sold: 1
Enter the number of Platinum tickets sold: 20

 Section    Tickets         Revenue
--------  ---------  --------------
  Silver  200000000  $7,000,000,000
    Gold          1             $55
Platinum         20          $1,700
========  =========  ==============
   Total  200000021  $7,000,001,755

Enter the number of Silver tickets sold: 2
Enter the number of Gold tickets sold: 5
Enter the number of Platinum tickets sold: 1

 Section  Tickets  Revenue
--------  -------  -------
  Silver        2      $70
    Gold        5     $275
Platinum        1      $85
========  =======  =======
   Total        8     $430