Cover image for blog post: "Much ado about Python."
Back to blog posts

Much ado about Python.

A personal reflection on going deep into Python through Fluent Python and Crafting Interpreters — covering CPython's indentation tokenizer, how sparse hash tables power dicts, and features like special methods, first-class functions, and runtime metadata.

Published onJune 25, 20266 minutes read

I have been reading through Fluent Python by Luciano Ramalho, and I realized I haven’t written anything about it. To be honest, I made the crucial mistake as a player in the tech space by not documenting my journey into, through, and around the tech space. Recently, I realized that being an unknown, very good front-end developer who could probably still spin up a quality backend system with Node.js is a good way to enjoy infinite unemployment in 2026. So now I am focusing less on my breadth of skills but on depth. I want to develop a skill where I am in the top 1% in the world, and that requires getting a lot of depth of knowledge on computers and the languages we use to speak to them.

I have been building backend systems with Python for 2 years now, but lately I realized I don’t know enough about the language; I only know how to use it. Yeah, so totally replaceable in the AI era. So yeah, I am now hitting as many books as I can, so I understand code and hardware in a way that allows me to develop things no one has ever seen before or that an AI can replicate.

I am not just reading Python for the sake of pulling out obscure Python facts at the next API conference. While my goal is to become a top 1% python developer, I have a more short-term goal of building a database using Python that solves a unique problem. I know. I know. Python is the fastest language in the world, but if you actually look into the language in depth, you’d realize that Python is just a specification on top of the much faster C code. You can make Python extremely fast; you don’t have to write C and a million declarations in header files to do it. I’d also like to take a crack and making a simple enough web framework after I understand coroutines in depth, I could make something interesting.

So that’s the backstory to my hero’s journey. Honestly, I really went down the wrong path in my early career until now. I got into programming when I had to read pages of C and C++ documentation to figure out, and every time I would find some new concept and syntax to help me towards my goal, it was so fun. That’s what made me miss out on. The fun you get from doing what you love. I wanna rediscover that love and build cool stuff along the way. Hopefully, I don’t starve while doing it.

Down the rabbit hole

Anyway, so I am also reading Crafting Interpreters by Robert Nystrom, which I recommend while you are learning about languages. It’s fun because you don’t just read about the different concepts and rules that define a language, but also the decisions and thinking that went into creating and evolving it. For example, Robert has a chapter on how the stream text is read and tokenized by a lexer or tokenizer. That got me curious about how the Python code is tokenized while keeping track of the indentation, which defines the different blocks and scopes.

I found out that CPython does this by keeping track of the indentation in two lists. One which counts the spaces and one which is used to count other forms of indentations like tabs, because to the user, they would be the 2 spaces could be the same as one tab shift. In this investigation, I found out that the Python parser does not care if the indentation space is smaller than the indentation of the outer scope. It will only throw an error if the indentation of an inner scope is more than the previous indentation. Pretty cool, right? Well, I admit it’s not that cool, but it would get you thinking about the intention of the different syntax rules in programming. The indentation is just to encode nesting depth, not visual consistency, so the tokenizer is not programmed to care.

How Python stores your data

Another interesting idea is the implementation of the dict data type or other mapping objects. Python uses sparse hash tables under the hood. So when an entry is to be added, the key is hashed, and based on the hash table, a particular slot on the table is allocated to that entry. If the system checks the slot and it is already occupied, then certain things happen:

Why this implementation, well, performance of course. Python relies a lot on the dict for much of its implementation, so dicts have to be really fast. Sparse hash tables are faster than others because, instead of the usual process of finding a new slot for an entry or finding a value for a particular key, which is usually expensive, sparse tables rely on an offset, which is a lot faster for a computer to execute (Computers love offsets). There is a large memory overhead, though we should be wary of how we use hash tables. Using tuples was possible instead.

Features worth knowing

Enough of my yapping about Python stuff. Let me get specific about some features I enjoy about Python that I have learnt about recently.

Special methods are pretty useful. Operator overloading is a thing in Java and C++, but it does require a lot of complex syntax to implement. Now, if you want to implement addition, for instance, you just need to write the __add__ function in the class declaration. There are many more useful special functions. Python will add the required syntactic sugar for you. So if you run a + b, it will look up the __add__ function, or maybe a == b, it will run the __eq__ special function. Do you need your object to be iterable then write out the __iter__ special method and return a iterable.

By the way, syntactic sugar is some syntax that is set up entirely for the benefit of the user writing the code. For example, for statements are generally considered syntactic sugar in every language because it’s really just the while loop with extra steps.

Functions are first-class objects: If a function can be assigned to a variable, changed at runtime, passed as a function parameter, or returned from another function, then functions are first-class objects in that language. Other languages do have this, but if you are coming from JAVA or c++, it would be pretty new to you. This does kinda eliminate the need for a lot of design patterns from the gang of Four design patterns book. There is a chapter in Fluent Python where Luciano makes a case that the Command pattern and the Strategy pattern can be implemented easily using functions in python. I also particularly like that you can make any instance callable by declaring the __call__ function for that object. You can create higher-order functions, which allow you to add some extra side effects to a function call. You can make use of that and free variables to perform logging or performance checks for each function call. This could be particularly useful for building a web framework because route endpoints will need to be tied to a route handler and monitored. BTW, decorators are basically higher-order functions that are declared at import time in Python.

I see metadata: Metadata tied to a function or instance is easily accessible in Python. For example, functions store the parameters in a dict object called __dicts__. Also, defaults for these parameters, as well as the information about the parameters, are provided. You can see the function annotations and type annotations. All these can be queried at runtime. This increases the flexibility of the use of functions and object instances, as you can modify behaviour based on what is noticed in the metadata at runtime.


That’s it for now. There are probably a lot of other aspects of the Python Programming Language worthy of note, but I decided to just write about those three for now. But as I learn more ways to be flexy with the reptilian language, I will update my thoughts in further writings.

Hope this was a fun read. I did get pretty honest, which is hard but rewarding to do, even if no one really reads this. The goal is to be consistent and in motion (hopefully forward). The journey to mastery should be an adventure, not just a commute. We all want to find the treasure on the grand blue line, but the journey to get there is the true One Piece.

PS. Have you noticed that there are three programming languages named after coffee? Programmers should really sleep more.