Splitting Images

I recently came across a problem where I had a single image with a transparent background containing multiple images that I wanted to split into their component parts. For example, split this:

Into these:


Ordering Board Game Geek GeekLists by Rank

A quick script.

I play a lot of board games. With the whole COVID-19 mess, I’ve been playing a lot on Board Game Arena, which is a wonderful site. But one thing that’s a bit lacking is having ratings / metadata about games to great games I’ve just not heard about before. Where can you get lots of that data? Board Game Geek!

The problem though, is merging the two. So, how do we do it? Well, this time around, I’m going to start with this GeekList that someone else maintains of BGA games on BGG. Which has the games, but no ranks. And apparently there are no ways to rank those by BGG (for some reason). But that’s easy when you know a bit of scripting!


Categorizing r/Fantasy Book Bingo Books

I’ve been working through the r/Fantasy 2021 Book Bingo this year:

2021 Book Bingo

SFF anthology or collection

Attack on Titan, Vol. 1

Set in Asia (Hard: by an Asian author)

r/Fantasy A to Z Genre Guide (Hard: by a BIPOC author)

Found Family (Hard: featuring an LGBTQ+ character)

First person POV (Hard: Multiple)

r/Fantasy Book Club (Hard: with participation)

New to you author (Hard: haven’t heard much about)

Gothic Fantasy (Hard: not in the Book Riot article)

Mexican Gothic

(Hard Mode)

Backlist book (Hard: published before 2000)

Revenge-seeking character (Hard: revenge as the major book plot)

Mystery plot (Hard: not primary world urban fantasy)

Six Wakes

(Hard Mode)

Comfort read (Hard: that isn’t a reread)

Wild Sign

(Hard Mode)

Debut novel (Hard: published in 2021)

Tales of Nezura: Book 1: The Zevolra

(Hard Mode)

Cat squasher (500+ pages; Hard: 800+ pages)

SFF-related nonfiction (Hard: published in the last 5 years)

Latinx or Latin American author (Hard: with fewer than 1000 Goodreads ratings)

Self published (Hard: with fewer than 50 Goodreads ratings)

Tales of Nezura: Book 1: The Zevolra

(Hard Mode)

Forest setting (Hard: for the entire book)


(Hard Mode)

Genre mashup (Hard: of three or more genres)

Gideon the Ninth

(Hard Mode)

Has chapter titles of more than one word (Hard: for every chapter)

The Midnight Library

(Hard Mode)

___ of ___ (Hard: and ___)

First contact (Hard: that doesn’t lead to war)

Project Hail Mary

(Hard Mode)

Trans or Nonbinary (Hard: protagonist)

Debut author (Hard: with an AMA)

Witches (Hard: as the main protagonist)

A Great and Terrible Beauty

(Hard Mode)


Partitioning a Linked List

One more fairly standard tech interview problem (for better or for worse, you’re likely to see one of these if you go for a programming job):

Given a linked list and an element x. Partition the list so that all elements less than x are before elements greater than or equal to x, but do not otherwise change the order of the elements.


Dynamic Programming over a Matrix

Another LeetCode problem. Given an MxN matrix of numbers, find the longest path of strictly increasing numbers. So for example in this matrix: 994 668 211 You can start with the 1 in the bottom center, go left to the two, then up to the 6, and 9. That’s the longest path, so return a 4. In this 3x3 case, it’s really easy to just brute force.


Phone Words--In English!

Okay, let’s take this one step further. Rather than generating just phone words, let’s actually generate phone words. Someone has provided a list of words in English as a package, so we’ll add a filter to add that to our comprehension: from english_words import english_words_set def letterCombinations(self, digits: str) -> List[str]: if not digits: return [] letters = { '1': '', '2': 'abc', '3': 'def', '4': 'ghi', '5': 'jkl', '6': 'mno', '7': 'pqrs', '8': 'tuv', '9': 'wxyz', '0': ' ', } return [ word for product in itertools.


Phone Words

Working through a few problems on LeetCode. I haven’t quite decided what I think of the site, but it’s a fun way to play with simple algorithms. Figured I might as well write up any I find interesting.

First interesting problem:

Given a standard lettered keypad, generate all words from a given phone number.


yt-cast: Generating podcasts from YouTube URLs

Today’s goal: Turn a collection of YouTube links into a podcast.

Start with a config.json like this:

  "brandon-sanderson": [

And it will automatically download all referenced YouTube videos, convert them to MP3 (both using youtube-dl), and serve an RSS feed that’s compatible with most podcast programs.

Tested URLs include:

  • Playlist URLs (like the above)
  • Single video URLs
  • Channel URLs

Most youtube URLs should work though.


Extending my EC2 script

Another quick post.

What feels like a lifetime ago, I wrote a post about finding ec2 instances by name. I honestly use that script just about every day, mostly for automatically finding instances to SSH to (a la SSH config tricks). But there are a few other quick things I’ve done with it:

  • ec2-script - Run a script on all instances of a given name
  • ec2-disk - A specialization of ec2-script to check main disk usage
  • terminate - A script that I use with ec2 to terminate instances from the command line
  • ec2-cycle - Slow cycle a given set of ec2 instances by terminating so many per minute

All of which are included in my dotfiles.


An SPF DNS Server

The Sender Policy Framework is one of those things that’s really powerful and useful to help prevent phishing and email spam, but can be a royal pain to work with. Specifically, SPF is a series of DNS TXT records1 with a specific format that can be looked up by any email service to verify that an email was sent by a server that should be authorized to send email on your behalf. For example

"v=spf1 ip4: ip4: a -all"
  • v=spf1 - tells the client this is an SPF record and should always start the record
  • {key}[:{value}]? - one of many different key/value pairs that can define the record
    • in the case above a ip4 key species an IPv4 address range that can send emails on your behalf (the value can be optional)
    • the a above is another special case where if the sender domain (jp@example.com would be example.com) resolves via a DNS A record to the server that sent the email, it’s allows
  • -all is a fallthrough case meaning ‘fail all that didn’t match a previous case

There are a number of other cases, but we’ll get to the other interesting ones in a bit.