Skip to main content

Welcome!

This is Derek Lam's personal site.
Let's get personal.
Scroll, I'll tell you a bit about myself.
Or just enjoy the Shard demo shown above

Spending time

There isn't much about any circuit that is uninteresting to me, so I took up work as a device engineer at Microchip's FPGA division designing next-generation non-volatile memories.

On my own, I develop Haskell program analysis tools. If you're interested, feel free to look through this symbolic execution engine and typesafe random program generator for Haskell.

Projects on this site

Presence Elsewhere

Email:
<my name>@lam.io
Resume:
everything here, but smaller

Recent Work

All Projects

Recent Projects

  • Jun 2020

    XKCD's Reaction Maps with n-gram matching

      I got a good laugh out of this recent XKCD strip, partly because I love puns, and partly because it's pretty hypocritical for Cueball to express his disdain for a one with 9 more:

      XKCD 2260

    • May 2020

      XKCD's phrase-to-units at high m·s-1

        In the previous installment of bastardizing the English language fun wordplay with Randall, we made a sentence-to-map-directions solver based on XKCD 2260. This time, we're in for something a little more scientific: a sentence-to-units solver based on the recent XKCD 2312. This time with unit symbols, we've got much smaller puzzle pieces to pack into phrases than we used to with towns, so we can aim for exact solutions. It turns out that people have made a lot of units, sometimes very weird ones, so we also shouldn't have much trouble getting at least the matching done.

        The real fun question is how to do good matching. Undoubtedly, the best solution is short and sweet, one that can take some crazy complicated rap and find that it's got units of flow [m3/s]. These units we give names to are generally simple in base unit terms, so a good proxy for an elegant algorithm is one that makes small base-unit terms.

      • Dec 2018

        Linear Tubular Motors

          Research on the efficiency and positioning abilities of these types of linear motors for the Extended Essay in Physics.

        • Nov 2018

          Slice

          Cutting polygons in realtime!

        • Nov 2018

          Procedural roadmap generation & SAE AutoDrive 2018 Competition Shirt

          As part of victory spoils, UofT's success in 2017 came with control over the competition shirt. I volunteered and inherited the responsibility, then promptly hot-potato'd it onto my computer to make most of the visually-interesting material. This emphasis on form was spurred by constraints on the color palette when only two tones are possible on top of the shirt's base color. In a similar vein but somewhat more timid on my processor than the goliath that is actual localization and mapping on Zeus, I built a simple tile-based procedural roadmap generator for an ornamental border, which I relate to ornamental vines on medieval texts. And OpenTTD.

        • Nov 2018

          Slice

            Cheesy? Maybe. Probably. Very. But the iconic trope of waving a sharp around an enemy and... for a split second, nothing happening! Then, the various segmented parts of the body start sliding along perfect planes onto the floor... it's timeless. Reality has a sad shortage of frictionless atom-thick blades, but hey I choose to install the physics engine if I want to!

            I did. This one. But I left out all the limiting parts nobody needs in a satisfying slicing demo, so you can demolish your favorite shape to your heart's content.

          • Oct 2017

            BlueDot EDIT Exhibit

            BlueDot Inc. is a company that analyzes the propagation of disease worldwide. With that description, it was a pleasant shock to be a part of an in-house Design Team in the summer of 2017. Getting to know BlueDot's products, with lots of data backing software and print products that needed to read crystal-clear, there was actually an unending barrage of challenging design work. I got to participate in a particularly exciting one when an opportunity to participate in the EDIT festival came up in the middle of the summer and we seized it. The festival pitted design and futurism against the 17 Millenium Goals, with showcases ranging from aquaculture to threats from globalization (us!) packed into the abandoned Unilever soap factory on the east end of Toronto. We chose to highlight the new "proximity" of the global neighbourhood with the proliferation of shorter and more frequent flights crossing the globe, and the fact that humans are not the only passengers on flights. SARS was an infamous example that locked the global flight network and still saw the cross-continental spread of the disease, consequently spurring the founding the lab that would become BlueDot.

            We were given a corner of the third floor propped between a floor manager's office box and a huge sliding doorway with about 10 feet in the middle.

          • Aug 2017

            DoubleRainbow

              People love rainbows. The problem is that forecasters lack the... well, foresight, to give the people the lucious rainbow details they want. The idea to fill this gaping hole in supply came from Akira Kakkar at MHacks 6, and I'm lucky to call him, Jenny Zhang and Philip Tsang my co-developers on the project for those critical first 36 hours. I personally released an alpha a year later because this project's momentum isn't allowed to stop. For the sake of all that is round and colorful.

              Detecting rainbows is feasible from just satellite and radar data, and boils down a geometry problem on these two datasets. From a quick detour into the mechanics of rainbows the problem statement will essentially just pop out.

            • Oct 2016

              Audiolizer

                Monstercat, an electronic label out of Vancouver, is near and dear to me since I grew into electronic music as Monstercat grew. If no part of its identity is spotless, at least the visualizer is and remains iconic without debate, even if not without its own slew of complaints. 63 bars, an equally stark Gotham presentation of artist and title, and across the boundary of its 5-year birthday in 2016, an ebb of particles, replaced later by animated album artwork, I respect its simplicity for showcasing the track.

              • Aug 2016

                RocScience UI, Print & Database design

                  Designed new iconset and UI for RS3 v2, created highly stylized illustrations and print handouts for conferences, heavy SQL crunching dirty CRM data.

                All Writing

                Writing

                1. Condensed Asterius quickstart

                  Here's an Asterius quickstart that aims to be a little more make-it-work-oriented than the official docs.

                  Coding

                2. deepseq for Data

                  Here's a very short but useful snippet I recently started using to force Data instances deeply:

                  {-# LANGUAGE Rank2Types #-}
                  import Data.Functor.Identity
                  import Data.Generics ( Data(..), GenericT )
                  
                  gmapT' :: GenericT -> GenericT
                  gmapT' f x0 = runIdentity (gfoldl k Identity x0)
                    where
                      k :: Data d => Identity (d->b) -> d -> Identity b
                      k (Identity c) x = Identity $! c $! f x -- let the user control strictness in `f`
                  
                  strictify :: GenericT
                  strictify = gmapT' strictify
                  
                3. Untitled

                  Hack is beginning to support reified types in their latest 4.17 release, which adds a very interesting dimension to Hack's type system. Its interactions with Hack's unique medley of type features can be quite subtle, and when any new type feature emerges, I always like to learn how and where it interacts with other features. To be more specific, I like to find this out by trying to break the new type system. So let's try together!


                  Hack's version of reified types enables two things:

                4. Simplifying reactive operators

                  I've argued that I have reason to believe that ReactiveX (Rx) is backwards. At first I promoted InteractiveX (Ix), which inverts the control, swapping callbacks for await. If you follow the road of trying to simplify Ix and its iterator acrobatics, I believe you'll arrive where I was, reimplementing Reagent. Originally built to shim all of JVM/JS's reactive interfaces into Kotlin's concurrency framework, the result ends up suiting async-await languages better than both Rx and Ix. For many details, see "Reagent is theoretically the best…", but in short, Reagent approaches an exact equivalence to natural code — an isomorphism to what you would write in that situation without the library. In particular, Reagent provides expressive and natural features to implement all aspects of an asynchronous loop to chomp away at a data source.

                5. Reagent is theoretically the best of ReactiveX

                  This extended article discusses the merits of Jake Wharton's Reagent framework for Kotlin which has deep theoretical advantages standing in for ReactiveX. I've stripped away any class definitions to make a lightweight functional version that I'll derive and justify from first principles here, with implementations for Hacklang, Javascript and Kotlin. Jake Wharton has put the project on hiatus, and while I agree that it's hard to fight the massive mindshare of ReactiveX, Reagent is at least a powerful lens to the semantics of streaming and the minimum that we require of our languages to make them reactive. At least I hope to convey that if one feels ReactiveX is wasteful on top of an async-await language, their feeling isn't wrong.

                  The maximum is in the middle

                6. Tracing values with state

                  The development of ra.hs has called for an interesting task in the domain of symbolic programming. ra.hs is a Haskell linter for reactive programs, the first implementation I'm undertaking to identify possible race conditions in reactive code. The violation to look for is a subtle one: if two threads consume the same stream and read and write these values to the same shared memory, the ordering rules of the stream might be violated [citation to come]. To decide this, it's necessary to trace the flow of values through the program to see which stream they come from, if any.

                  The degree of sophistication of analysis against the program could be incredibly varied, bounded above only by the undecideability of the halting problem (fun fact: with probability 1, halting can actually be decided). I believe that it's meaningfully bounded below by a type analysis, where the conditional nature of branches is ignored and all values that are the correct type that could flow to a call site are considered. This allows for a perfectly sensitive result that sacrifices specificity (i.e. it may report many false positives).

                7. Guide to InteractiveX in Kotlin

                  I was just peeking at Kotlin to see if they supported asynchronous generators. I wasn't expecting much, because when I was making InteractiveX implementations for PHP and Hack last year, Kotlin coroutines weren't publicly documented. Man, I got way more than I bargained for. I knew even just looking at this title to this guide in kotlinx.coroutines:

                  Guide to reactive streams with coroutines

                8. How to make a ReactiveX

                  I was tipped off to Reactive Frameworks from @Robert Harvey on a long-winded StackExchange question of mine for what "reactive databases" were called. I was infatuated with Hack's elegant async API and let me tell you it absolutely expanded my world in all the right ways.

                9. Why ReactiveX operators are hard to make and InteractiveX operators aren't

                  Full-featured reactive stream libraries, like Rx, come with a very large set of operators to create, transform, combine and otherwise process the corresponding streams. Creating your own operators with support for back-pressure is notoriously difficult.

                  Coroutines and channels are designed to provide an opposite experience. There are no built-in operators, but processing streams of elements is extremely simple and back-pressure is supported automatically without you having to explicitly think about it.

                  from Kotlin's guide to reactive channels

                10. Kotlin Coroutines: How SelectBuilder magically pulls coroutines out of the select block

                  I was puzzled for a while about the syntactic sugar around select — Kotlin's experimental feature to process streams from multiple sources (docs). Take a look at this:

                  fun main() = runBlocking<Unit> {
                  	select<Unit> {
                  		launch {
                  			delay(100)
                  		}.onJoin { Unit }
                  		produce {
                  			delay(200)
                  			send("foo!")
                  		}.onReceive { Unit }
                  	}
                  }