Introspection in Python
Introspection in Python refers to the ability of a program to examine the type or properties of an object at runtime. It is a powerful feature of Python, leveraging its dynamic nature.
Key Features of Introspection
-
Type Checking:
- You can check the type of an object using the
type()orisinstance()functions. - Example:
x = 42 print(type(x)) # Output: <class 'int'> print(isinstance(x, int)) # Output: True
- You can check the type of an object using the
-
Inspecting Attributes and Methods:
- Use the
dir()function to list all attributes and methods of an object. - Example:
print(dir(str)) # Lists all methods and attributes of the string class
- Use the
-
Getting Documentation:
- Access an object’s documentation string using the
help()function or.__doc__attribute. - Example:
print(help(len)) # Displays documentation for the `len` function print(str.__doc__) # Displays the docstring of the string class
- Access an object’s documentation string using the
-
Determining Base Classes:
- Use the
__bases__attribute to find the base classes of a class. - Example:
class MyClass: pass print(MyClass.__bases__) # Output: (<class 'object'>,)
- Use the
-
Inspecting Module Contents:
- Use
dir()on a module to list its contents. - Example:
import math print(dir(math)) # Lists all functions and constants in the math module
- Use
-
Accessing Object Attributes:
- Use
getattr(),setattr(), andhasattr()to dynamically interact with attributes of an object. - Example:
class MyClass: x = 10 obj = MyClass() print(getattr(obj, 'x')) # Output: 10 setattr(obj, 'y', 20) print(hasattr(obj, 'y')) # Output: True
- Use
Why Introspection is Useful
- Debugging: Easily inspect objects to understand their properties and methods.
- Dynamic Programming: Create adaptable and flexible programs that can handle unknown types at runtime.
- Reflection: Perform operations like dynamically calling methods or inspecting classes.
Example: Introspection in Action
class Animal:
def speak(self):
return "I am an animal"
obj = Animal()
# Introspection example
print(type(obj)) # Output: <class '__main__.Animal'>
print(dir(obj)) # Lists all attributes and methods of the object
print(obj.speak()) # Output: I am an animal
Introspection allows Python programs to be highly dynamic and flexible by enabling runtime examination of objects. It is a cornerstone of Python’s dynamic typing and reflective capabilities.
```python
# Example 1: Type Checking
x = 42
print(type(x)) # Output: <class 'int'>
print(isinstance(x, int)) # Output: True
# Example 2: Inspecting Attributes and Methods
print(dir(str)) # Lists all methods and attributes of the string class
# Example 3: Getting Documentation
print(help(len)) # Displays documentation for the `len` function
print(str.__doc__) # Displays the docstring of the string class
# Example 4: Determining Base Classes
class MyClass:
pass
print(MyClass.__bases__) # Output: (<class 'object'>,)
# Example 5: Inspecting Module Contents
import math
print(dir(math)) # Lists all functions and constants in the math module
# Example 6: Accessing Object Attributes
class MyClass:
x = 10
obj = MyClass()
print(getattr(obj, 'x')) # Output: 10
setattr(obj, 'y', 20)
print(hasattr(obj, 'y')) # Output: True
print(obj.y) # Output: 20
# Example 7: Introspection in Action
class Animal:
def speak(self):
return "I am an animal"
obj = Animal()
# Introspection example
print(type(obj)) # Output: <class '__main__.Animal'>
print(dir(obj)) # Lists all attributes and methods of the object
print(obj.speak()) # Output: I am an animal
Interview angle
- “What introspection tools do you actually use?” -
type,isinstance,dir,vars,getattr, andinspectfor signatures and source. In debugging,inspect.signatureandinspect.getsourceanswer most “what does this actually accept” questions faster than reading imports. - “How do frameworks use it?” - FastAPI reads type annotations from the signature to build validation and OpenAPI; pytest discovers fixtures by parameter name; ORMs read class attributes to build schemas. Introspection is what makes declarative Python APIs possible.
- “When is it the wrong tool?” - when a Protocol or explicit registration would be clearer. Heavy runtime introspection makes code hard to follow statically and defeats type checkers.