Category Archives: Software Development

Learn by Cloning

The App-o-Mat website was mostly written in 2013. The backend is in Django, and over time I have had to constantly upgrade that, so now it’s on pretty modern Django and Python 3.

The frontend is simple HTML, but uses Bootstrap and a bootstrap template for layout and styling. I decided it was time to abandon that and just build it on CSS Flex and Grid. The styling isn’t complex, so I can easily write the CSS for that.

I found this YouTube video to be a great whirlwind tour to implementing a design in modern CSS.

He mostly just plows along and does it, which was good enough for me.

In my version, I am learning from the lessons of Tailwind and relying nearly 100% on utility classes (or by selecting tags classlessly), so that I can do everything I need from the markup and inside server-side components. I would use Tailwind, but it’s overkill for my system, and I am sick of updating dependencies for this site.

In the end, the site should be pretty much the same, except with no Bootstrap and fairly simple CSS that I can maintain going forward.

The Amazing Voice Master

In yesterday’s episode of Write While True, I spoke about how making things changes you. This is true even if what you made isn’t that great. I asked you to think about the programs you threw away.

In my morning pages today I tried to start from the first program I ever wrote and think about all the small things I made and never finished. I hadn’t thought about it in years, but I reminded myself of the Amazing Voice Master and found an ad for one in the Internet Archive’s Compute! Magazine archive.

The Voice Master ad claimed it could turn humming into sheet music, but I guess I didn’t hum in tune.

I mostly remember making card games that responded to voice, which worked a little better, but I did learn to be skeptical of voice recognition claims. Perhaps that prepared me to do my Skillshare course and Smashing article on Siri.

Design by Opposite Example: Nebulous

Yesterday I wrote about a way to think about designing something: by comparing opposites. I also think you can use the idea of opposites to generate a new thing from something else.

This is an exercise I did recently to design a game.

I call it Nebulous, because it’s meant to be a play on a “nebula”, which I am thinking of the opposite of an asteroid. Nebulous is the opposite of Asteroids.

Here are some essential elements of Asteroids

  1. It is about survival through evasion and destruction. You die if you touch an asteroid (or spaceship or get shot)
  2. The camera is stationary in space
  3. The game surface is the finite surface of a torus (it wraps on the sides)
  4. It is black and white
  5. All of the game elements are a stroked white shape
  6. You pilot a ship that can thrust, rotate, fire, and hyperspace

I used this to generate what could be the essential elements of Nebulous

  1. It is about survival though finding and nurturing. You die if you run out of energy, which you get by flying through a nebula.
  2. The camera follows the ship
  3. The game surface is infinite in all directions
  4. It uses color. Each nebula has a color and the color indicates its behavior. Mixing colors is part of game play
  5. (not sure yet of the design language)
  6. You pilot a ship that only has two thrusters. You turn by using just one of them. You can eject stored nebula gases.

I am still thinking about this. At this point, I don’t need to keep thinking about the opposite of Asteroids — this starting point will be the seed that goes in its own direction from here.

My Third Lesson in Personal Finance: Optionality

My early career was in writing financial options software, so I’ve been around the concept for options for a long time. The general characteristic that’s important to understand is that it has a fixed, low cost and a (low-relative-probability) of very high upside.

My ex-boss, Philip Brittan, wrote this piece about optionality back in 2014 on an internal blog and recently posted it publicly. It goes over the technical details, but generally, when I read it I was reminded about the power of the generic concept of options when applied more broadly.

He ended: “In general, you should be on the lookout for situations that naturally make you long options and give an asymmetrical (‘unfair’) advantage”. (being “long options” means you have options — as opposed to short, where someone has options on you).

Applied broadly, there are many things that “have optionality”. For example, renting instead of buying. But, for now, let’s concentrate on optionality in compensation.

At the time I read this, I was consulting. The kind of optionality that consulting offers is options on opportunity and freedom. You can easily change what you are doing or when and where you work. You can stop and start at will, comparatively. But, in consulting, pay is mostly tied to work and does not have options-like returns.

Before that, and for most of my career, I worked for startups that had some kind of optionality in the pay structure. My first job had an unlimited profit-sharing bonus pool that was literally a percent of profit that was not capped. At other times I had equity-like instruments, options, or RSUs. I also did limited work for free for a share in future profits.

My personal finance plan was just a normal compounded returns and high savings with an exponential curve, but when I look at what actually happened, there are these moments of step-wise lumps when one of these options paid off. I was lucky, for sure, but also, I took a lot of shots.

The key was that my options mostly felt free to me. I was completely satisfied with the job and guaranteed pay, so the option was extra. It might be true that I could get more elsewhere, but I was satisfied.

My default plan would still work.

I think of optionality in compensation the way some people think about playing the market with “play money”. I’d be ok if the options expired worthless. It’s another way I think programmers can “beat the market” with labor instead of by picking stocks.

Consider C4 for Systems Interviews

I recently ran into the C4 model for visualizing software architecture. It’s simple and notation agnostic (meaning, you don’t need to learn the meaning of arrow heads).

One of the things I noticed in giving systems interviews is that the interviewee didn’t have any kind of coherent way to visualize their system. So, it was hard to understand what they were saying.

The benefit of C4 is that it’s just slightly more organized than doing nothing. It also asks that you provide a key/legend for any notation choices you make.

I think that most of the benefit comes from the suggestions to use more text. For example:

Boxes have a name, type, and a short description. Think of it like this: NAME is a TYPE that DESCRIPTION.

A C4 container box that describes "Sprint-o-Mat' as a watchOS App that guides you during an outdoor run

Arrows form a sentence when read as “BOX A” — “arrow text” –> “BOX B”.

A C4 container diagram that says that Sprint-o-Mat stores workouts in HealthKit

The idea is that the diagrams are stand-alone and are mostly organizing short text snippets.

They are also hierarchical—meaning that if I need more information, there would be possibly be a set of sub-diagrams for each box. Without C4, I think many people would just have the boxes with just the names (titles) and unlabeled arrows.

The metaphor is a map that starts zoomed out and gets more and more detail as you zoom in.

I am mostly suggesting this as a sketching/communication visualization using a whiteboard. But if you are trying to do C4 to keep real diagrams, then generating them from some kind of DSL is much better. PlantUML provides a free solution, and the author of C4 has a freemium solution called Structurizr.

Using Market Data in the Python Net Worth Estimator

When I first made the python version of the net worth spreadsheet, I used a function like this:

def netWorthByAge(
    ages, 
    savingsRate = 0.18, 
    startingNetWorth = 10000,
    startingSalary = 40000,
    raises = 0.025,
    
    marketReturn = 0.06,
    inflation = 0.02,
    
    retirementAge = 65
  ):

You could pass in parameters, but only constants. This is how the spreadsheet works as well—each cell contains a constant.

The first thing to do to make it more flexible is to use a lambda instead for the marketReturn parameter:

marketReturn = (lambda age: 0.06),

Then, when you use it, you need to call it like a function:

netWorth = netWorth * (1 + marketReturn(age - 1)) + savings

We use last year’s market return to grow your current net worth and then add in your new savings.

The default function is

(lambda age: 0.06)

This just says that 0.06 is the return at every age, so it’s effectively a constant.

But, instead, we could use historical market data. You can see this file that parses the TSV market data file and gives you a simple function to look up a historical return for a given year.

Then, I just need to create a lambda that looks up a market rate based on the age and starting year:

mktData = mktdata.readMktData()
for startingYear in range(fromYear, toYear, 5):
  scenario = networth.netWorthByAge(ages = ages,
    savingsRate = savingsRate, 
    marketReturn = (lambda age: mktdata.mktReturn(mktData, age, startingYear = startingYear))
  )

And this will create a scenario (an array of doubles representing net worth) for each year in the simulation.

You can download and run the code to play with it. Here’s a sample chart it generates:

There are lines for starting the simulation in 1928, 1933, 1938, 1943, 1948, 1953, and 1958. This gives you an idea of the expected range of possibilities.

How Programmers Can Beat the Market

In my last few posts I’ve been trying to model net worth over time as a function of savings. In my last post, I used real historical market data instead of a constant 6%. Looking at a few scenarios, the market returned more like an average of 9.5% over those time periods.

I still think you should use 6% in your plans (if it’s actually 9.5% in the next 60 years, then that’s good news—you can make adjustments every decade if you are way ahead of plan).

Reminder: I am not a financial advisor and this is not advice. I don’t know anything about your personal situation. Talk to a fiduciary if you want advice.

But, you might think: “I bet I can beat the market—I understand tech/bitcoin/stonks better than most people.”

It’s not likely.

S&P keeps a scorecard of actively managed funds against their benchmarks. In a single year, active funds may do ok against the market, but go to page 9 and look at their longer term performance. 75% don’t beat the S&P 500 over 5 years, and 94% don’t beat it in 20.

These are funds with professionals with a staff who spend all day, every day thinking about this and are paid based on performance. You can beat 94% of them by just putting your money in an index fund.

But, then what do you do with all of that free time?

To beat the market, remember that you are also a player in a market. If you work full-time, you are in the labor market. You could also create products and sell them (in the market).

Look at your current net worth. To pick a random number, let’s say it’s currently 100k. If the market returns 6%, you’ll have 6k more at the end of the year. If you try to beat the market by picking stocks, and get 10%, you have made $4k more. Let’s say your net worth is $500k. Working to get that 10% return will get you an extra $20k.

Is this really the best way to make an extra $4-20k? It’s not a sure thing—you might not beat the market (like over 50% of active managers each year). You could lose money.

So, instead, invest in yourself.

To “invest” in the labor market, you could take courses to make yourself worth more and then either ask for a raise or change jobs. You could raise your profile with an open-source project, writing, or by giving talks. You do not need to be “famous” to do this. Your projects or work don’t need a million followers. You could beat the market with a few dozen.

Outside of your job, you could seek side-income. If you make $100/hour, you only need 40 hours of consulting (less than 1 hour/week) to “beat the market”. Technically, you beat the market in your first hour.

Or with your first sale.

And there aren’t a lot of costs to consulting, e-books, or software (other than your own time). But, at least you know that the time spent will net a positive return. Even if you make no sales, it’s pretty likely that you have made yourself more valuable.

If you spend 40 hours and make $4k in the market, that’s a one-time effect. You haven’t made yourself more valuable, and it’s unlikely you can do this year after year. If you get a $4k raise, your salary is $4k higher the next year too. Beating the market is automatic and you can build on it.

More good news: the less you money you have, the more “return” you can make this way. If you have $10k in the bank, making $10k on the side doubles your net worth. Getting a $5k raise is like a 50% return.

You can’t beat that picking stocks.