Generics in Python
Our example demonstrates the use of generic functions and types in Python. Python has supported generics since version 3.5 through type hinting, and more advanced generic features were introduced in version 3.10.
from typing import TypeVar, Generic, List, Sequence, Any
# As an example of a generic function, `slices_index` takes
# a sequence of any comparable type and an element of that
# type and returns the index of the first occurrence of
# v in s, or -1 if not present.
T = TypeVar('T')
def slices_index(s: Sequence[T], v: T) -> int:
for i, item in enumerate(s):
if item == v:
return i
return -1
# As an example of a generic type, `LinkedList` is a
# singly-linked list with values of any type.
class LinkedList(Generic[T]):
class Node(Generic[T]):
def __init__(self, val: T):
self.val = val
self.next = None
def __init__(self):
self.head: LinkedList.Node[T] | None = None
self.tail: LinkedList.Node[T] | None = None
def push(self, v: T) -> None:
new_node = self.Node(v)
if self.tail is None:
self.head = new_node
self.tail = new_node
else:
self.tail.next = new_node
self.tail = new_node
def all_elements(self) -> List[T]:
elems = []
current = self.head
while current:
elems.append(current.val)
current = current.next
return elems
def main():
s = ["foo", "bar", "zoo"]
# When using generic functions, Python's type inference
# automatically determines the types.
print("index of zoo:", slices_index(s, "zoo"))
# We can also specify the types explicitly if needed.
_ = slices_index[str](s, "zoo")
lst = LinkedList[int]()
lst.push(10)
lst.push(13)
lst.push(23)
print("list:", lst.all_elements())
if __name__ == "__main__":
main()
To run the program:
$ python generics.py
index of zoo: 2
list: [10, 13, 23]
This Python code demonstrates the use of generics through type hinting. The slices_index
function is a generic function that works with any sequence of comparable items. The LinkedList
class is a generic type that can hold elements of any type.
In Python, we use the TypeVar
and Generic
constructs from the typing
module to define generic types. The T = TypeVar('T')
creates a type variable that can be used in generic functions and classes.
The Sequence
type hint is used instead of a specific list type to allow for any sequence-like object (lists, tuples, etc.). The Any
type is used when we need to indicate that a value can be of any type.
Note that while Python’s type hints provide static type checking capabilities, they are optional and do not affect the runtime behavior of the program. Tools like mypy can be used to perform static type checking based on these hints.