Encapsulation
Getters and Setters
Pythonic attribute access with @property
Interview: Encapsulation — tests understanding of @property, computed attributes, and Pythonic vs Java-style access control
In Python, getters and setters are implemented using the @property decorator, not explicit get_name()/set_name() methods like in Java. The Pythonic approach lets you start with plain attributes and upgrade to managed access later without changing the API. This is a fundamental difference from Java's "always use getters/setters" philosophy.
Pythonic vs Java-Style
- Pythonic: Use plain attributes, upgrade to @property when needed
- Java-style: Always use get_x()/set_x() — not Pythonic!
- @property lets you add validation/computation without breaking callers
- Callers use
obj.radiusregardless of whether it's a plain attr or property
When to Use Properties
- Adding validation to attribute assignment
- Computing derived values (e.g., full_name from first_name + last_name)
- Making attributes read-only (no setter)
- Adding side effects (logging, cache invalidation)
Common Pitfall
Don't create Java-style getters/setters in Python. If you don't need validation or computation, use plain attributes. obj.get_name() and obj.set_name(v) are considered unpythonic.
Use Cases
Input validation on attribute assignment (email format, positive numbers)
Computed/derived properties (full_name, area, age from birthdate)
Read-only attributes (id, created_at, login_count)
Lazy loading expensive computations (cache on first access)
Backward compatibility: upgrade plain attrs to properties without changing API
Common Mistakes
Creating Java-style get_x()/set_x() methods instead of @property
Making everything a property when plain attributes would suffice
Naming property same as backing field causing infinite recursion
Defining setter without getter (@property must come first)
Using properties for expensive operations (should be methods, not attributes)