log.nikhil.io

5 things tagged “computer science”

Functions, Monoids, Functors, Monads

Started with this blog post about why one would need a monad (from a typing standpoint.) Then watched “What the 𝒇 is a Monad” which made a lot of things clear. Then watched this excellent, excellent talk on Lambda Calculus (with JS and Haskell code!) by Gabriel Lebec.

Finished with a quick practical, toy example by @mpjme and this Scala horror-show (to me.)

State, Coupling, Complexity, & Code

Dependencies (coupling) is an important concern to address, but it’s only 1 of 4 criteria that I consider and it’s not the most important one. I try to optimize my code around reducing state, coupling, complexity and code, in that order.

I’m willing to add increased coupling if it makes my code more stateless.

I’m willing to make it more complex if it reduces coupling.

And I’m willing to duplicate code if it makes the code less complex.

Only if it doesn’t increase state, coupling or complexity do I dedup code.

The reason I put stateless code as the highest priority is it’s the easiest to reason about. Stateless logic functions the same whether run normally, in parallel or distributed. It’s the easiest to test, since it requires very little setup code. And it’s the easiest to scale up, since you just run another copy of it. Once you introduce state, your life gets significantly harder.

I think the reason that novice programmers optimize around code reduction is that it’s the easiest of the 4 to spot. The other 3 are much more subtle and subjective and so will require greater experience to spot. But learning those priorities, in that order, has made me a significantly better developer.

crun1r on HackerNews (emphases and formatting mine.)

❣️


Jan 12 On “incidental duplication”:

I’ve usually heard this phenomenon called “incidental duplication”, and it’s something I find myself teaching junior engineers about quite often.

There are a lot of situations where 3-5 lines of many methods follow basically the same pattern, and it can be aggravating to look at. “Don’t repeat yourself!” Right?

So you try to extract that boilerplate into a method, and it’s fine until the very next change. Then you need to start passing options and configuration into your helper method… and before long your helper method is extremely difficult to reason about, because it’s actually handling a dozen cases that are superficially similar but full of important differences in the details.

I encourage my devs to follow a rule of thumb: don’t extract repetitive code right away, try and build the feature you’re working on with the duplication in place first. Let the code go through a few evolutions and waves of change. Then one of two things are likely to happen:

  1. you find that the code doesn’t look so repetitive anymore, or,
  2. you hit a bug where you needed to make the same change to the boilerplate in six places and you missed one.

In scenario 1, you can sigh and say “yeah it turned out to be incidental duplication, it’s not bothering me anymore.” In scenario 2, it’s probably time for a careful refactoring to pull out the bits that have proven to be identical (and, importantly, must be identical across all of the instances of the code).

burlesona on HackerNews (emphasis and formatting mine.)

Whatever. I say we continue to abstract away and make better and better hammer factories and beam at our sophistication in creating unnecessary complexity #jobsecurity

Numbering from Zero

Dijkstra on why numbering should start from zero.

Numbering is done with natural numbers. Let’s take zero to be the smallest natural number1. For the sequence (2, 3, 4, … ,12), using the convention (2 ≤ n < 13) is appropriate because

  • For a sequence starting with zero, like (0, 1, 2, 3), the left hand condition leaks into unnatural numbers if you use “less than”: (-1 < n).
  • For an empty sequence, the right hand also leaks into the unnatural if you use “less than or equal to”: (n ≤ 0)

And minorly, because these are the true of another convention (1 < n ≤ 12)

  • Difference between bounds (13 - 2 = 11) is the length of the sequence
  • I know that these two sequences are adjacent: (2 ≤ n < 13) and (13 ≤ n < 24)

All that’s prep for:

When dealing with a sequence of length N, the elements of which we wish to distinguish by subscript, the next vexing question is what subscript value to assign to its starting element. Adhering to convention a) yields, when starting with subscript 1, the subscript range 1 ≤ i < N+1; starting with 0, however, gives the nicer range 0 ≤ i < N. So let us let our ordinals start at zero: an element’s ordinal (subscript) equals the number of elements preceding it in the sequence. And the moral of the story is that we had better regard – after all those centuries!2 – zero as a most natural number.

There’s also this little nugget

I think Antony Jay is right when he states: “In corporate religions as in others, the heretic must be cast out not because of the probability that he is wrong but because of the possibility that he is right.”

  1. TIL that this can be so. ↩︎

  2. Don’t know what he means here… ↩︎

Winter Coding Challenges

On the Turing-Completeness of PowerPoint

A tongue-in-cheek presentation on the Turing-Completeness of Powerpoint. This is some astounding PowerPoint-fu. Reminded me of the words of Linus Torvalds, “That is either genius, or a seriously diseased mind.” 😛