So you want to get better with Python? One of the best things you can do to practice is get to know the Python standard library. This is the collection of modules that come packaged with the language and it includes practically everything you need to build applications. Whether it’s servers, parsers, or email applications, it’s got you covered.
One of my favorite modules from the standard library is
collections. It’s got a couple of key tools for common, everyday Python programming. It provides you with specialized dictionaries, lists and tuples.
Today, I’m going to talk about
When I first learned about them, I was building endpoints for an API for my team. The problem I was trying to solve was this: how do I create specialized object types to aid with organizing my code — without creating new classes?
namedtuple provided a very elegant solution. Here’s a simple example of how you might use them:
from collections import namedtuple ApiRequest = namedtuple('ApiRequest', ['status', 'method', 'details']) response = ApiRequest(200, 'GET', 'Request was awesome!') response.status # => 200
The equivalent class code would be:
class ApiResponse: def __init__(self, status, method, details): self.status = status self.method = method self.details = details response = ApiResponse('201', 'GET', 'Document created.')
As you can see, the
namedtuple is something of a shorthand for creating classes of objects, but it’s got some great features out of the box that ordinary classes don’t have. Some benefits I was looking for:
- Immutable: I needed objects that would never be altered.
- Identifiers: I needed objects whose attributes were simple to access.
- Reusable: It had to be something others on my team could quickly re-use and understand at a glance.
namedtuple is very Pythonic; it makes your code more readable, efficient and brief. You’ll also hear the term “self-documenting” used to describe them, which is what makes them easy to understand at a glance. You and your team don’t have to go to a different file and read class definitions to know what the code is doing or how to use it.
Now, I could’ve used a dictionary to handle the data instead, but I’d have to use bracket notation or dictionary methods like
dict.get(). That’s not a great hassle, but it’s not as elegant as the
namedtuple and it doesn’t provide immutability, identifiers or ease of use.
namedtuple can be easily converted to a dictionary if needed with a handy helper method:
In addition to these benefits, there’s more. A
namedtuple can be subclassed, meaning you could add methods to them.
class CustomRequest(ApiRequest): def is_success(self): if self.status == 200: return True return False response = CustomRequest(200, 'The request had no problems.') response.is_success # => True
The next time you’re building something with Python or refactoring code, think about how you might use the
collections.namedtuple to make your code more pythonic, efficient and clean.