, ,

How Do You Format Text and Numbers in Python? (Python for Beginners, Part 10)

Work with strings in Python, clean them with methods, and use f-strings to place values and format decimals, width, and alignment. Print a tidy receipt.

Python for Beginners · Part 10 of 20

Here is the same total printed two ways. One looks like a machine dumped it; the other looks like a receipt.

output
Total:160.5
Total          160.50

The numbers are identical. Only the formatting changed. This part is about text in Python: how strings work, the handful of things you do to them most, and the tool that makes output look deliberate instead of accidental. That tool is the f-string, and by the end of this part your expense tracker prints a clean receipt.

Bottom lineA string is text. You can slice it, change its case, strip stray spaces, and paste values into it. The value you paste in is done with an f-string: put an f in front of the quotes and drop any variable inside curly braces. Add a colon and a format code to control decimals, width, and alignment.

This part assumes Part 9, where you wrapped your add and print steps in functions. You need Python 3 and about twenty five minutes. Every snippet runs as printed. If you type along, you will reproduce each result exactly.

Strings, and the quotes around them

A string is a run of characters: letters, digits, spaces, punctuation. You write one by wrapping text in quotes. Single or double both work, and they behave identically:

python
name = 'Asha'
city = "Pune"
print(name, city)
output
Asha Pune

The reason both exist is so you can put one kind of quote inside the other without a fight. If your text contains an apostrophe, wrap it in double quotes:

python
note = "it's lunch"
print(note)
output
it's lunch

Picking single or double

Pick one and stay consistent. This series uses single quotes, and switches to double only when the text itself contains an apostrophe. There is no speed or correctness difference. Consistency is the whole point, because mixed quoting is one more thing for your eyes to trip on when you scan code later.

Things you can do to a string

Strings come with built-in tools called methods. You call a method by putting a dot and its name after the string. Each one returns a new string and leaves the original untouched, which surprises beginners: a string never changes in place.

python
raw = '  Groceries  '
clean = raw.strip()
print(clean)
print(clean.upper())
print(clean.replace('c', 'C'))
output
Groceries
GROCERIES
GroCeries

You can also measure a string with len() and pull out pieces by position. Positions start at zero, not one, which is the second thing that trips beginners.

python
word = 'python'
print(len(word))
print(word[0])
print(word[0:3])
output
6
p
pyt
You want toMethod or toolExample result
Remove edge spaces.strip()‘ hi ‘ becomes ‘hi’
Upper or lower case.upper() / .lower()‘Hi’ becomes ‘HI’
Swap text.replace(a, b)‘cat’ becomes ‘car’
Count characterslen(s)‘python’ gives 6
Split on a separator.split(',')‘a,b’ becomes [‘a’, ‘b’]

Table 1. The string tools you will reach for most in your first months.

f-strings: putting values inside text

You often want to build a sentence out of values you already have. The old way was gluing pieces with plus signs, and it forced you to convert numbers to text by hand:

the clumsy way
amount = 120.5
line = 'Spent ' + str(amount) + ' today'
print(line)
output
Spent 120.5 today

The f-string does the same thing without the noise. Put an f before the opening quote, then drop any value inside curly braces. Python fills each brace with the value:

the clear way
amount = 120.5
line = f'Spent {amount} today'
print(line)
output
Spent 120.5 today
f’Spent {amount} today’ 120.5 the variable value drops into the braces

Figure 1. The braces mark a slot. Python replaces the slot with the value.

Controlling how a number looks

The real power shows up when you add a colon and a format code after the value. This is where a bare number becomes money. A few codes cover almost everything you will need:

python
price = 1250.5
print(f'{price:.2f}')
print(f'{price:,.2f}')
print(f'{price:>10.2f}')
output
1250.50
1,250.50
   1250.50
Format codeWhat it does1250.5 becomes
:.2fTwo decimal places1250.50
:,.2fThousands separator plus decimals1,250.50
:>10Right align in a width of 10right padded
:<10Left align in a width of 10left padded
:^10Center in a width of 10centered

Table 2. The format codes that turn raw numbers into tidy columns.

Gotcha: the missing fIf you forget the f before the quotes, Python does not fill the braces. It prints them literally, and there is no error to warn you:
output
Spent {amount} today
When output shows braces instead of a value, the cause is almost always a missing f. Check the front of the string first.

Splitting text apart and joining it back

Real data often arrives as one line of text with separators, and you need the pieces out of it. Two methods handle almost all of that work. .split() breaks a string into a list on a separator, and .join() glues a list back into a single string. They are opposites, and together they cover most day to day text handling.

python
row = 'food,120.5,lunch'
parts = row.split(',')
print(parts)
print(parts[0])
print(parts[1])
output
['food', '120.5', 'lunch']
food
120.5

Notice the amount came back as text, not a number. Splitting always yields strings, so you convert before doing any maths on them. That is a real trap, and Part 12 handles it head on.

Going the other way, .join() takes a list and glues it with the separator you call it on:

python
fields = ['travel', '40', 'cab']
line = ','.join(fields)
print(line)
output
travel,40,cab

One catch trips people the first time. .join() only works on a list of strings. Hand it a number and Python stops with a clear last line:

output
TypeError: sequence item 1: expected str
instance, int found

Read that last line the way Part 2 taught. It wanted a string and found an int, so convert numbers with str() before joining. This split and join pair is exactly how a program reads and writes simple data files, which is where the next part goes.

In practiceWhen you read a line back from a file or an API, it arrives as one long string. The first thing you usually do is .split() it into fields, and the last thing before saving is .join() them back. Getting fluent with this pair now makes the file work in Part 11 feel like something you have already done.

When formatting goes too far

f-strings let you put whole expressions inside the braces, and that is where people overreach. You can write a brace that does a calculation, calls a function, and formats the result all at once. You should usually not. Here is the kind of line that looks clever and reads badly:

hard to read
print(f'{sum(x["amt"] for x in items):,.2f}')

Pull the work out into a named step, then format the plain result. The two line version is longer and much easier to trust:

easier to trust
total = sum(x['amt'] for x in items)
print(f'{total:,.2f}')

My rule, and it goes against the tidy one liner advice you will see: a brace should hold a value or a simple attribute, not a computation. If you need a calculation, give it a name on its own line first. You are not being paid by the fewest lines. You are paid to write code the next person can read, and that person is often you in three months.

A tidy receipt for the tracker

Your expense tracker can now print output that looks intentional. Building on the functions from Part 9, here is a print_receipt that lines up categories on the left and amounts on the right, then totals them. Every value is placed with an f-string and a format code.

expenses.py
expenses = [
    {'amount': 120.5, 'category': 'food'},
    {'amount': 40, 'category': 'travel'},
]

def print_receipt(items):
    cat_head = 'Category'
    amt_head = 'Amount'
    print(f'{cat_head:<12}{amt_head:>10}')
    print('-' * 22)
    total = 0
    for item in items:
        cat = item['category']
        amt = item['amount']
        print(f'{cat:<12}{amt:>10.2f}')
        total += amt
    print('-' * 22)
    label = 'Total'
    print(f'{label:<12}{total:>10.2f}')

print_receipt(expenses)
output
Category        Amount
----------------------
food            120.50
travel           40.00
----------------------
Total           160.50

The <12 pads each category to a width of twelve on the left, and the >10.2f right aligns each amount in a width of ten with two decimals, so the numbers stack in a clean column. This is the same skill every report, invoice, and log line in real software depends on.

Why this matters in your first jobReports and logs are read by people. A column of amounts that lines up, with consistent decimals, is the difference between output someone trusts at a glance and output they have to squint at. New engineers who format their print statements and log messages cleanly look careful, and careful is the reputation you want in month one. This is a small habit that people notice.
Real interview question"How would you print a price with exactly two decimal places?" The answer they want is an f-string with a format code: put the value in braces and add :.2f, as in a format like f'{price:.2f}'. A strong follow up is mentioning :,.2f for a thousands separator. It is a small question that quickly shows whether you have actually formatted output or only ever printed raw values.
Try it yourselfYou have item = 'coffee' and price = 4.5. Print one line that reads exactly coffee costs 4.50, with the price shown to two decimal places. Expected output:
expected output
coffee costs 4.50
Show solution
python
item = 'coffee'
price = 4.5
print(f'{item} costs {price:.2f}')

Two slots in one f-string. The first drops in the text as is, the second formats the number to two decimals with :.2f.

String questions people actually ask

Why did my string not change after I called .upper()? Because string methods return a new string and never edit the original. Capture the result: name = name.upper(). If you throw the result away, nothing seems to happen.

What is the difference between an f-string and .format()? They do the same job. The f-string reads better because the value sits right where it appears in the text. Older code uses .format(); new code should default to f-strings.

Can I put an f-string across several lines? Yes. Wrap it in triple quotes and it keeps your line breaks, or use n inside a normal f-string to force a new line where you want one.

How do I show a real curly brace in an f-string? Double it. {{ prints one {, and }} prints one }. This comes up when you build things like JSON by hand.

Is there a quick way to print a variable name and value while debugging? Yes, and it is genuinely handy: f'{price=}' prints price=4.5. The equals sign inside the braces shows both the name and the value.

You can nowYou can now build strings, clean and reshape them with methods, place values inside text with f-strings, and control decimals, width, and alignment so output lines up. Your tracker prints a real receipt. In Part 11 it stops forgetting: you save those expenses to a file so they survive after the program closes.
price = 1250.5a floatf'{price:,.2f}’1,250.50
An f-string reads the value, applies the format spec, and returns finished text.
Python for Beginners · Part 10 of 20
« Previous: Part 9  |  Complete Guide  |  Next: Part 11

About The Author


Discover more from Journal of Intelligent Infrastructure – By Dr Pranay Jha

Subscribe to get the latest posts sent to your email.

Leave a Reply

Your email address will not be published. Required fields are marked *

Architect’s Toolkit

About the Author

Dr. Pranay Jha is a Cloud and AI Consultant with 18+ years of experience in hybrid cloud, virtualization, and enterprise infrastructure transformation. He specializes in VMware technologies, multi-cloud strategy, and Generative AI solutions. He holds a PhD in Computer Applications with research focused on Cloud and AI, has published multiple research papers, and has been a VMware vExpert since 2016 and a VMUG Community Leader.

Discover more from Journal of Intelligent Infrastructure - By Dr Pranay Jha

Subscribe now to keep reading and get access to the full archive.

Continue reading