Fix TypeError: not all arguments converted during string formatting (Python)

Updated Oct 23, 2023 β€³ 5 min read

Python’s “TypeError: not all arguments converted during string formatting” error is raised for the following reasons:

  1. When you’re formatting a string (and the number of placeholders and values don’t match up)
  2. When calculating a division’s remainder (and the lefthand-side operand is a string rather than a number)

🎧 Debugging Jam

Calling all coders in need of a rhythm boost! Tune in to our 24/7 Lofi Coding Radio on YouTube, and let's code to the beat – subscribe for the ultimate coding groove!" Let the bug-hunting begin! πŸŽ΅πŸ’»πŸš€

24/7 lofi music radio banner, showing a young man working at his computer on a rainy autmn night with hot drink on the desk.

Here’s what the error looks like:

Traceback (most recent call last):
  File, line 4, in <module>
    print('Hi %s' % (first_name, last_name))
TypeError: not all arguments converted during string formatting

When you're formatting a string

As you probably know, Python supports various ways of formatting strings (a.k.a string interpolation):

  1. Old string formatting with the % operator
  2. str.format()
  3. Formatted String Literals (a.k.a f-strings)

1. Old string formatting with the % operator

In the old string formatting (a.k.a printf-style string formatting), we use the % (modulo) operator to generate dynamic strings:

string % values

The string operand is a string literal containing one or more placeholders identified with a % character. The values operand can be a single value or a tuple of values. These values replace the placeholders in the string (in the order they're defined)

Here's an example:

first_name = 'Tom'
last_name = 'Jones'

print('Hi dear %s' % first_name)
print('Full name: %s %s' % (first_name, last_name))

And the output would be:

Hi dear Tom
Full name: Tom Jones

The letter s following the % character is called a format specifier. In this case, we're specifying the replacement value is a string.

However, if you're inserting a digit, you can use %d specifier instead.

βœ‹ Watch out for: This type error occurs when you supply more values than the existing placeholders in your format string syntax:

first_name = 'Tom'
last_name = 'Jones'

print('Hi %s' % (first_name, last_name))

You'll even get this error if you have supplied values, but there's no placeholder in the string:

first_name = 'Tom'
last_name = 'Jones'

print('Hi' % first_name)

So if you're using the old-style string formatting, ensure the number of placeholders and replacement values match up.

2. Format String Syntax (str.format())

A more robust way of formatting strings in Python is using the str.format() method, a.k.a Format String Syntax.  

In Format String Syntax, you define a literal text containing replacement fields (surrounded by curly braces). Then, you call format() on it to provide values for those replacement fields.

first_name = 'Tom'
last_name = 'Jones'

print('Hello, {0} {1}').format(first_name, last_name)
# Output: Hello, Tom Jones

When passing positional arguments to the format() method, you can omit positional argument specifiers, like so:

first_name = 'Tom'
last_name = 'Jones'

print('Hello, {} {}').format(first_name, last_name)
# Output: Hello, Tom Jones

Additionally, you can use keyword arguments with the format() method:

first_name = 'Tom'
last_name = 'Jones'

print('Hello, {fname} {lname}').format(fname=first_name, lname=last_name)
# Output: Hello, Tom Jones

3. Formatted String Literals

You can use Formatted String Literals (also called f-strings for short) as an alternative to str.format(). Formatted string literals let you include any Python expression inside a string. You create an f string by prefixing it with f or F and including expressions inside curly braces.

first_name = 'Tom'
last_name = 'Jones'

print(f'Hello, {first_name} {last_name}')
# Output: Hello, Tom Jones

F-strings are what you might want to use for string interpolation.

βœ‹ Watch out for: Based on some threads on StackOverflow, some users had mixed up the old formatting syntax with the new string formatter. For instance, they used curly braces in the old string formatting syntax:

first_name = 'Tom'
last_name = 'Jones'

# Raises the error
print('Hello {} {}' % (first_name, last_name))

You must use the modulo (%) operator when using the prinf-style string formatting.

When calculating a division's remainder

As you probably know, the % (modulo) operator is used for two purposes in Python:

  • Old string formatting: string % values
  • Getting a division's remainder: 12 % 2

That said, you might also get this error when trying to get the remainder of a division but the lefthand operator is a string (instead of a number).

When the % follows a string, Python considers the expression to be string formatting syntax - rather than a mathematical expression.

The following code is supposed to print "n is Even!" if the n is an even number.

n = '12'

if (n % 2 == 0):
    print('n is Even!')

However, it raises the type error; The reason is Python's interpreter considered it to be an interpolation expression.

If you got the number via the input() function, you have to cast it to a number first:

n = '13'

if (int(n) % 2 == 0):

Problem solved!

Alright, I think it does it! I hope you found this quick guide helpful.

Thanks for reading.

Disclaimer: This post may contain affiliate links. I might receive a commission if a purchase is made. However, it doesn’t change the cost you’ll pay.