Data Types and Structures
Casting, also called type conversion, is converting a value from one data type to another. You cast a value when it is the wrong type for the operation you need to perform: arithmetic needs numbers, joining text with + needs strings, a comparison such as greater than needs two values of the same type, and writing a line to a file needs text.
Python 3 has a built-in function for each of the main data types, named after the type it produces. Each call returns a value of that type.
| Function | Value it returns |
|---|---|
int() | integer |
float() | real number |
str() | string |
bool() | Boolean |
Two more functions work on single characters. ord() returns the integer character code (its ASCII value) of a character, and chr() turns a code back into a one-character string.
A conversion function returns a new value. It does not change the original variable unless you assign the result. For example, converting a text value to an integer gives a new integer; the original text variable still holds the text.
price_text = "12.50"
quantity_text = "3"
price = float(price_text) # assign the new real number
quantity = int(quantity_text)
total = price * quantity
print("Total: " + str(total) + " pounds")Output:
Total: 37.5 pounds
You can combine casting with other operations in one expression, provided the order is correct. The innermost call runs first, so wrapping input() in float() reads text and then converts it. Choose the target type to suit the job: integer or real for arithmetic, string for concatenation, Boolean for decisions, and a character code when you need to move between a character and its ASCII value.
The Programming Language Subset uses these same functions: convert data to the right type for the next step, such as turning text input into a real number before a calculation, or a number into a string when building an output line. Correct casting keeps a program robust, because mismatched types cause runtime errors that stop the program.
int() and float() are the Python functions that convert a value to an integer or to a real number.
int() converts a valid whole-number string, such as "42", or a real number into an integer. When you pass it a real number, the fractional part is removed by truncation towards zero, which is not the same as rounding. For example, int(8.7) gives 8 and int(-8.7) gives -8, because both values move towards zero. So 8.7 does not become 9; if that was your intention you would need round() instead.
float() converts a valid numeric string, such as "3.25", or an integer into a real number. float(6) gives 6.0, which is a real number that happens to have nothing after the point. You use it when a value needs to keep its decimal part, such as a price in pounds and pence or a measured length in metres.
Boolean values convert to integers too: int(True) gives 1 and int(False) gives 0, because a Boolean is stored as 1 or 0, with 1 meaning True and 0 meaning False. In the other direction, an integer becomes a real number with float(), and a real number becomes an integer with int(), losing the fractional part as described above.
| value | int(value) | float(value) |
|---|---|---|
| "42" | 42 | 42.0 |
| 8.7 | 8 | 8.7 |
| -8.7 | -8 | -8.7 |
| 15 | 15 | 15.0 |
| True | 1 | 1.0 |
# truncating a real number towards zero
race_time = 47.62
whole_minutes = int(race_time)
print(whole_minutes)
# turning an integer into a real number
runners = 12
runners_as_real = float(runners)
print(runners_as_real)
# a Boolean becomes 1 or 0
finished = int(True)
print(finished)Output:
47
12.0
1
Both functions return a new value rather than changing the one you give them, so race_time still holds the real number while whole_minutes holds the integer.
The str function converts a value into its string representation: the text form of that value. You use it when a number or Boolean needs to become text, usually so it can be joined to other text.
str works on an integer, a real number or a Boolean. It returns a new string that looks like the original value, but it is text. For example, the integer 37 becomes the string "37", the real number 2.75 becomes "2.75", and the Boolean False becomes "False".
| Value | Type | String produced |
|---|---|---|
| 37 | Integer | "37" |
| 2.75 | Real number | "2.75" |
| False | Boolean | "False" |
The + operator joins two strings together, but it cannot join a string to a number. If you try to add text such as "Score: " to the integer 18, Python cannot make one string and the program stops with a runtime error. You must convert the number with str first, then join the resulting string to the text.
A print call with comma-separated arguments is different. It displays the arguments as separate items and does not build one concatenated string. To make one string, join the pieces with + and use str on any number or Boolean.
This program builds a single report string from a team name, an integer, a real number and a Boolean.
team = input("Enter team name: ")
points = int(input("Enter points: "))
average = float(input("Enter average score: "))
captain = True
report = team + " scored " + str(points) + " points"
report = report + " with an average of " + str(average)
print(report)
print("Captain present: " + str(captain))Output when the user types Falcons, 23, 4.5:
Enter team name: Falcons
Enter points: 23
Enter average score: 4.5
Falcons scored 23 points with an average of 4.5
Captain present: True
Each str call changes a non-string value into text before the + joins it to the rest of the report.
Boolean conversion uses the bool() function to turn a value into either True or False. Python checks whether the value counts as empty or zero, not what the value looks like.
These values convert to False:
0 or 0.0''None, which means no value at allEvery other value converts to True, including negative numbers such as -6, real numbers such as 0.5, and any collection holding at least one item.
A string converts to True when it holds at least one character. Python never reads the word and decides what it means; it only checks whether the string is empty. So 'False', '0', 'no' and even a single space ' ' all convert to True. The empty string '' is the only string that converts to False.
| Value | bool(value) | Reason |
|---|---|---|
0 | False | zero counts as empty |
14 | True | not zero |
'' | False | no characters |
'False' | True | five characters, so not empty |
' ' | True | one space character |
None | False | no value |
print(bool(0)) # zero
print(bool(14)) # a non-zero number
print(bool('')) # empty string
print(bool('False')) # non-empty string
print(bool(' ')) # one space characterOutput:
False
True
False
True
TrueThe program shows the same rule at work. Zero counts as empty, so it converts to False, while a non-zero number is True. The string 'False' is judged on its five characters alone, so it converts to True even though the word looks like a false value.
In Python 3 there is no separate character data type. A single character such as "G" is a string of length one: the value is text even though it contains only one character, even when that character looks like a digit.
Each character has an ASCII code, the integer used to represent it. For example, the uppercase letter "G" has the ASCII code 71. Converting between a character and its code is a type conversion (casting), and the direction matters.
| Function | Takes | Returns | Example |
|---|---|---|---|
ord() | a character | an integer ASCII code | ord("G") gives 71 |
chr() | an integer ASCII code | a character | chr(71) gives "G" |
ord() takes a one-character string and returns its integer ASCII code, so ord("G") gives 71. It needs exactly one character, so ord("GC") raises an error. chr() takes an integer ASCII code and returns a one-character string, so chr(71) gives "G". Using them the wrong way round, such as ord(71) or chr("G"), raises an error because each function is handed the wrong type of value.
# ord() turns a character into its ASCII code
code = ord("M")
print(code)
# chr() turns an ASCII code back into a character
print(chr(code))Output:
77
MIn Python 3, the input() function always gives you back a string, even when the user types nothing but digits. A string is text, so it records the characters that were typed rather than a numeric value you can do arithmetic with.
Type 250 at an input() prompt and you get the string "250" — three separate characters, not one value. Python reports the length of the string as 3, and each digit is stored as its character code. A number such as 250 is stored as a single binary value instead. Because the two are stored differently, digits that look like a number do not behave like one in arithmetic.
Use a string of digits in arithmetic such as subtraction and you get a runtime error: Python cannot subtract text. Comparing text with a number using a comparison operator such as less than also raises an error. Even the + operator joins two strings rather than adding, so "12" + "8" gives "128", not 20.
Use casting to turn the string into a number. Wrap input() in int() for whole numbers, or in float() when the value may have a decimal part. You can convert in the same statement that reads the input, or store the text in a variable first and convert it afterwards.
laps_text = input("How many laps did you swim? ")
laps = int(laps_text) # convert the stored text to a whole number
lengths = laps * 2
print("That is " + str(lengths) + " lengths of the pool")Output when the user types 12:
How many laps did you swim? 12
That is 24 lengths of the pool
price = float(input("What is the price of the hoodie? "))
change = 20 - price
print("Change from twenty pounds: " + str(change))Output when the user types 14.75:
What is the price of the hoodie? 14.75
Change from twenty pounds: 5.25
Text read from a file behaves the same way: every field arrives as a string, even one that looks like a number. Convert each field with int() for whole numbers or float() for decimal values before you add it to a total or compare it.
Casting errors happen when a value is the wrong data type for the operation you use it in, or when a conversion function cannot make sense of the text you give it. The program runs until it reaches the bad line, then stops with a runtime error.
Using text where a number is needed, or joining text to a number with +, raises a runtime error. For example, + between a string and a number fails because Python cannot decide whether you want addition or concatenation. The value must be cast first: use int() or float() to turn numeric text into a number before calculating, and str() to turn a number into text before joining it to a string.
name = "Priya"
age = 15
print(name + age) # text plus numberOutput:
TypeError: can only concatenate str (not "int") to str (line 3)
Conversion is strict. int() only accepts text that is a valid whole number, and float() only accepts text that is a valid real number. The string "19 goals" contains extra characters, so int("19 goals") fails rather than picking out the 19. Letters, punctuation, spaces between digits and an empty string all cause the conversion to fail.
score = int("6.5")
print(score)Output:
ValueError: invalid literal for int() with base 10: '6.5' (line 1)
A string with a decimal point cannot go straight to an integer. int("6.5") fails because the decimal point is not part of a whole number. Convert to a real number first with float("6.5"), then to an integer with int(...) if you need one. The order matters: the float conversion handles the decimal point before the integer conversion removes the fractional part.
Casting works on one value at a time. The functions str(), int(), float() and bool() each take a single value and return a converted copy of it, and none of them converts the items inside a list, array or record one by one. A structured data type therefore has each element cast separately, wherever that element is used.
If you pass a list to str(), Python converts the container's own printed form. That form keeps the punctuation that shows the structure: square brackets around the items, quotation marks around any text and commas between the items. A shopping list of three items becomes one long string such as ['bread', 'milk', 'eggs'], with brackets and quotes mixed in among the words. That is not the clean comma-separated data line a file needs, and a program reading it back would treat the brackets and quotes as part of the data.
The same is true in the other direction. int() expects one valid number string or number, so handing it a whole list or record makes the program fail rather than converting the items inside.
Suppose a swimming club stores three race times as text: "31", "28" and "35". To add them up, cast each one with int() at the moment you use it, so each conversion acts on a single element. The total can then be turned back into text with str() so that it can be joined to a label.
| Data held | Casting the whole structure | Casting each element |
|---|---|---|
| Three prices stored as text: "2.50", "1.20" and "3.00" | str() keeps the brackets and quotation marks, giving one messy string | float() on each price gives 2.5, 1.2 and 3.0, which can be added |
| A record holding a name and a score | The cast keeps the field names and the punctuation around them | str() on the score alone, so it can be joined to text |
A quick check: if the value you hand to a cast holds more than one item, you are converting the container, not its contents.