Sign in to your Python Morsels account to save your screencast settings.
Don't have an account yet? Sign up here.
Let's talk about how to create a multi-line string in Python without accidentally indenting the text within that string.
Here we have a function that prints out a copyright statement:
def copyright():
print("""\
Copyright (c) 1991-2000 ACME Corp
All Rights Reserved.
Copyright (c) 2000-2030 Cyberdyne
All Rights Reserved."""
)
This function works, but the copyright statement that it prints out is indented:
>>> copyright()
Copyright (c) 1991-2000 ACME Corp
All Rights Reserved.
Copyright (c) 2000-2030 Cyberdyne
All Rights Reserved.
Each line in this copyright statement begins with eight spaces. This happens because in our code, the text within our string begins with eight spaces before each line.
We can fix this problem by manually dedenting the text within this string:
def copyright():
print("""\
Copyright (c) 1991-2000 ACME Corp
All Rights Reserved.
Copyright (c) 2000-2030 Cyberdyne
All Rights Reserved."""
)
While this does work:
>>> copyright()
Copyright (c) 1991-2000 ACME Corp
All Rights Reserved.
Copyright (c) 2000-2030 Cyberdyne
All Rights Reserved.
This also makes our code a bit tricky to read.
Our code is less readable than before because up here, we our code suddenly dedents in the middle of our string.
We could fix this problem in by using the dedent
function in Python's textwrap
module.
textwrap.dedent
to unindent stringsThe dedent
function allows us to indent our code however we'd like.
Our multi-line string can be nicely indented in our code because the dedent
function will will dedent it for us:
from textwrap import dedent
def copyright():
print(dedent("""\
Copyright (c) 1991-2000 ACME Corp
All Rights Reserved.
Copyright (c) 2000-2030 Cyberdyne
All Rights Reserved."""
))
At the point where we use this string, we'll see that it doesn't have any indentation:
>>> copyright()
Copyright (c) 1991-2000 ACME Corp
All Rights Reserved.
Copyright (c) 2000-2030 Cyberdyne
All Rights Reserved.
The dedent
function removed the indentation for us.
Note that our string starts with a backslash (\
):
from textwrap import dedent
def copyright():
print(dedent("""\
...
))
That backslash removes the extra newline character (\n
) that this string would start with if this backslash weren't here.
Without that backslash, we would need to start our text on the same line to avoid that newline character:
from textwrap import dedent
def copyright():
print(dedent("""Copyright (c) 1991-2000 ACME Corp
...
Note that we're also ending our multi-line string on the same line that our text ends:
from textwrap import dedent
def copyright():
print(dedent("""\
...
All Rights Reserved."""
))
It would be nice if we could end it on the next line instead, but that would add an extra newline at the end of our string.
I prefer to combine dedent
with the string strip
method to take care of these newlines.
dedent
with strip
to make the code more readableHere we're using the strip
method with our string:
from textwrap import dedent
def copyright():
print(dedent("""
Copyright (c) 1991-2000 ACME Corp
All Rights Reserved.
Copyright (c) 2000-2030 Cyberdyne
All Rights Reserved.
""").strip("\n"))
The dedent
function is dedenting a string that starts with a newline character and ends with a newline character (note that we end our multi-line string on the next line).
After we dedent, we then use the string strip
method to remove those newline characters.
Our copyright statement looks as it should:
>>> copyright()
Copyright (c) 1991-2000 ACME Corp
All Rights Reserved.
Copyright (c) 2000-2030 Cyberdyne
All Rights Reserved.
And we have nicely indented code that doesn't have a strange backslash. Plus we don't need to worry about where exactly our multi-line string ends in our code: we're ending our string on the new line and that's okay!
dedent
maintains relative indentation levelsIt's important to note that the dedent
function doesn't remove all whitespace from the beginning of each line.
It's a little bit smarter than that.
The dedent
function maintains relative indentation within a string.
Here we have a string that is expected to have some lines indented more than others:
from textwrap import dedent
example_list = dedent("""
- Fix leap year bug
- User registration breaks on leap years
- Write a regression test
- Record a screencast
""").strip("\n")
print("The list.txt file should show a bulleted list, like this:")
print(example_list)
You can see that every line has at least four spaces of indentation, but some lines have more indentation.
When we run dedent
against this string, you'll see the four spaces of indentation (that's common to each line) is removed:
$ python3 example_list.py
The list.txt file should show a bulleted list, like this:
- Fix leap year bug
- User registration breaks on leap years
- Write a regression test
- Record a screencast
But the indentation that some lines have (that is relatively greater than other lines) is maintained.
textwrap.dedent
to unindent stringsIf you'd like to nicely format your multi-line string within your Python code without printing indented text by mistake, you can use the dedent
function from Python's textwrap
module.
Need to fill-in gaps in your Python skills?
Sign up for my Python newsletter where I share one of my favorite Python tips every week.
Need to fill-in gaps in your Python skills? I send weekly emails designed to do just that.