Learning From Python Enhancement Proposals
I've been playing with CircuitPython for my latest microcontroller project, and so far I've been impressed by how well it brings Python benefits (like managing asynchronous execution) to modest hardware. But taking full advantage requires person writing the code to know how to leverage those Python benefits. I've had experienced Python developers say my Python code reads like C code, failing to take advantage of what Python has to offer. I think it's a valid observation! But I don't learn well reading a long spec end to end. I need to write some code in between reading documentation to give context for the concepts I'm reading. Some code, some documentation, back to code, repeat.
And I think my CircuitPython adventures have reached a good stopping point. My motivation is to better understand what I've been using to deal with asynchronous serial data transmission and reception between my microcontroller and the NEC K13988 chip in charge of a salvaged Canon Pixma MX340 multi-function inkjet control panel. I got as far as creating an instance of asyncio.lock
and calling "async with
" that lock. I copied that straight from sample code and it was an opaque magical incantation to me. While I understood the high level concepts of synchronization, I have no idea how Python language syntax used those keywords. So, time to pause coding and hit the books!
One of the great things about Python is that its evolution takes place out in the open. Many features can be traced back to a corresponding design document called a Python Enhancement Proposal. A PEP distills information from many sources. Discussions on mailing lists, forums, etc. While design of a Python feature is usually summarized in a PEP, not all PEP intend to add Python features. PEPs are used for other things including best practice procedure recommendations for Python contributors. For example, I was amused by the fact that PEP #1 is for PEP itself, PEP Purpose and Guidelines.
A PEP for a feature will typically refer to precedence and possibly alternate proposals for that feature. This ancestry tree of PEPs is great for learning how a feature came to be. Sometimes a feature directly builds upon another, sometimes a feature has no direct technical relationship to another but the syntax is designed so existing Python developers will find it familiar. It also tends to mean I have to at least skim those earlier PEPs to understand what the current PEP is talking about. It will take effort to not get too distracted.
I will try to stay focused on my objective: understand what "async with
" does. Documentation search pointed to PEP 492 Coroutines with async and await syntax. Which mostly focused on the "async
" part, assuming I was already familiar with "with
". My understanding is still shaky so I will also need PEP 343 The “with” Statement. Both PEP 492 and 343 pointed to PEP 342 Coroutines via Enhanced Generators as highly relevant.
I think getting through this trio will give me a good start. A single step in the long journey to make my Python code look like Python and not just C code translated to Python syntax. Unfortunately, I have a hard time staying focused on study time.