Python

Python Data Types | Strings Numbers Collections

Master strings, numbers, collections, and datetime for effective programming

By InventiveHQ Team

Python's core data types break down into a few clear families: text (str), numbers (int, float, complex, bool), sequences (list, tuple, range), mappings (dict), sets (set, frozenset), binary data (bytes), and the special None value. Everything in Python is an object, and every value has exactly one type that you can inspect with type(value). The single most useful distinction to learn early is mutable vs. immutable: whether a value can be changed in place after it is created — because that one property governs how assignment, copying, and function arguments behave.

That is the tidy summary an AI Overview will hand you. What it will not show you is which type to reach for in a given situation, the Python-2-era myth that trips up beginners (there is no separate "long" type anymore), or how mutability quietly changes the behavior of your code. The diagram, the decision table, and the worked examples below cover exactly that.

The Python type map at a glance

Map of Python's built-in data types grouped by category and mutability Python built-in types organized into text, numbers, sequences, mappings, sets, and none, with mutable types highlighted in blue and immutable types in amber. Python Built-in Data Types Blue = mutable (changeable in place) · Amber = immutable (fixed once created) Text str "hello", 'P', """multi""" Numbers int float complex bool is a subclass of int Sequences list tuple range ordered, index access Mappings dict key → value pairs Sets set frozenset unique items, no order Binary & None bytes bytearray None raw bytes & absence of value Why mutability matters Mutable: two names can point to the SAME object — a change through one is seen by the other. Immutable: "changing" a value actually creates a new object, leaving the original untouched.
Advertisement

Strings and characters

Strings are ordered, immutable sequences of Unicode characters. Python has no separate character type the way C does — a single character is just a string of length one. You can write string literals with single quotes, double quotes, or triple quotes for multi-line text; they are equivalent.

name = "Python Programming"
character = "P"
print(name)          # Python Programming
print(character)     # P
print(len(name))     # 18
print(name.upper())  # PYTHON PROGRAMMING
print(name)          # Python Programming  <- original is unchanged

Because strings are immutable, methods like .upper() and .replace() return a new string. If you try to assign into a string by index (name[0] = "J") Python raises a TypeError. To build a string efficiently in a loop, gather the parts in a list and call "".join(parts) once at the end.

Numbers

Python has three numeric types plus a boolean type. Note the common myth: Python 3 does not have a separate "long integer" type. That was a Python 2 distinction. In Python 3 the single int type has arbitrary precision, so it grows to hold numbers as large as your memory allows — no overflow, no special syntax.

integer_num = 42
float_num = 3.14
complex_num = 2 + 3j
huge = 2 ** 1000        # a 302-digit int, no overflow

print(type(integer_num))  # <class 'int'>
print(type(float_num))    # <class 'float'>
print(type(complex_num))  # <class 'complex'>
print(True + True)        # 2  <- bool is a subclass of int
TypeExamplePrecision / notesReach for it when
int42, -7, 2**1000Arbitrary precision, never overflowsCounting, indexing, whole-number math
float3.14, -2.5, 1e964-bit IEEE 754, ~15–17 significant digitsMeasurements, ratios, scientific values
complex2 + 3jReal + imaginary partsSignal processing, engineering math
boolTrue, FalseSubclass of int (1 and 0)Flags, conditions, counting truthy items
DecimalDecimal("0.1")Exact base-10 (from the decimal module)Money and anything where 0.1 + 0.2 != 0.3 matters

For currency, avoid float0.1 + 0.2 famously evaluates to 0.30000000000000004. Use decimal.Decimal (or integer cents) instead.

Collections

Collections store multiple items. The four built-in workhorses differ along three axes: ordered vs. unordered, mutable vs. immutable, and whether duplicates are allowed.

fruits = ["apple", "banana", "cherry"]              # list
person = {"name": "John", "age": 30, "city": "NYC"} # dict
coordinates = (10, 20)                               # tuple
unique_numbers = {1, 2, 3, 4, 5}                     # set

Which collection should I use?

CollectionSyntaxOrdered?Mutable?Duplicates?Use it when
list[1, 2, 3]YesYesYesA general-purpose, changeable sequence
tuple(1, 2, 3)YesNoYesA fixed record, or a key in a dict/set
dict{"k": "v"}Yes (3.7+)YesKeys uniqueLookups by name/key; structured records
set{1, 2, 3}NoYesNoDeduplication and fast membership tests

A quick rule of thumb: if you need to look things up by name, use a dict; if you need fast "is this in here?" checks or to remove duplicates, use a set; if order and mutation matter, use a list; if the data should never change, use a tuple. Dicts and sets rely on hashing, which is why their keys/members must themselves be immutable (you can use a tuple as a dict key, but not a list).

Date and time

Dates and times get their own types from the datetime module. You can store a date as a string, but a real datetime object gives you arithmetic, comparison, formatting, and timezone handling for free.

from datetime import datetime, timedelta

now = datetime.now()
print(now)                                  # 2026-07-18 14:05:32.115003

tomorrow = now + timedelta(days=1)          # date arithmetic
print(tomorrow)

formatted = now.strftime("%Y-%m-%d %H:%M:%S")  # format to string
print(formatted)                            # 2026-07-18 14:05:32

parsed = datetime.strptime("2026-07-18", "%Y-%m-%d")  # string back to datetime
print(parsed.year)                          # 2026

The advantage is concrete: with real datetime objects you can subtract two dates to get a timedelta, sort a list of events correctly, and convert to and from strings deliberately with strftime/strptime. Two dates stored as plain strings cannot be subtracted or reliably compared without converting them first.

Inspecting and converting types

Every value carries its type. Use type() to see it and isinstance() to test it — isinstance is preferred in real code because it also matches subclasses.

value = 42
print(type(value))              # <class 'int'>
print(isinstance(value, int))   # True

# Explicit conversion ("casting")
print(int("100"))     # 100    (str -> int)
print(str(3.14))      # '3.14' (float -> str)
print(float("2.5"))   # 2.5    (str -> float)
print(list("abc"))    # ['a', 'b', 'c']
print(set([1, 1, 2])) # {1, 2}  (dedupe)

Python is dynamically typed (a variable can be rebound to any type) but strongly typed (it will not silently add a string to an integer — "3" + 5 raises a TypeError). Knowing which built-in type you are holding, and whether it is mutable, is most of what you need to write correct, predictable Python.

Frequently Asked Questions

What are the main data types in Python?

Python's built-in types fall into a handful of groups: text (str), numbers (int, float, complex, and bool), sequences (list, tuple, range), mappings (dict), sets (set, frozenset), binary data (bytes, bytearray), and the special None value (NoneType). Everything in Python is an object, so type(x) will always return one of these classes.

Does Python have a separate "long" integer type?

No. That was a Python 2 concept. In Python 3 there is a single int type with unlimited (arbitrary) precision, so 2 ** 1000 just works without overflow. Any tutorial listing "long integer" as a distinct Python 3 type is out of date.

What is the difference between a list and a tuple in Python?

A list is mutable (you can add, remove, or change items after creation) and is written with square brackets: [1, 2, 3]. A tuple is immutable (fixed once created) and is written with parentheses: (1, 2, 3). Use a list for a changing collection and a tuple for a fixed record or a dictionary key.

Is a string mutable in Python?

No. Strings are immutable. Methods like .upper() or .replace() return a brand-new string rather than changing the original. If you need to build up text in a loop efficiently, collect the pieces in a list and join them with "".join(parts).

How do I check the type of a variable in Python?

Use the built-in type() function, for example type(42) returns <class 'int'>. To test whether a value belongs to a type (including subclasses), use isinstance(x, int), which is the preferred check in real code because it also handles inheritance.

Why should I use datetime objects instead of storing dates as strings?

A datetime object supports arithmetic (add a timedelta), comparison, formatting with strftime, parsing with strptime, and timezone handling. A date stored as a string is just text, so you cannot subtract two of them or sort them reliably without converting first.

What is the difference between a set and a list?

A set is an unordered collection that automatically removes duplicates and offers very fast membership tests (x in my_set). A list keeps insertion order and allows duplicates. Convert a list to a set with set(my_list) to deduplicate it, but you lose ordering in the process.

Are Python dictionaries ordered?

Yes, since Python 3.7 dictionaries preserve insertion order as a language guarantee. Earlier versions did not, which is why some older code uses collections.OrderedDict. In modern Python a plain dict keeps keys in the order you added them.

Is bool a number in Python?

Technically yes. bool is a subclass of int, so True equals 1 and False equals 0. That means True + True evaluates to 2, and you can sum a list of booleans to count how many are True.

Advertisement