The Zen Of Python, One-Liners and Being Pythonic

Today, Carlton Gibson posted a wonderful short programming question:

I love little questions like this, and instantly came up with a solution. However, before I shared what I came up with, I took a quick look at the answers, and saw a bevy of very creative solutions.

None of these felt like an awesome solution for me. I’ve had some similar thoughts on some related matters, and it felt like time for a blog post.

Continue reading

The Thing I Hate About Distributed Systems

I’ve always been fascinated with distributed systems.  It’s awesome that although we haven’t seen much in terms of increase of processing power, but instead we are moving to multi-core commodity hardware and scaling horizontally across it.  When I just started professionally programming, distributed systems just meant you had a handful of programs keeping in concert with each other of sockets, each doing different pieces of the solution.   It was a simpler time.

Now, you’re talking about a much more massive scale.  I contribute IoT and cloud services like AWS or GCP with the rise of accessibility for making distributed programs easy.  There’s also a slew of tools that are awesome and specifically designed for managing distributed systems.  Kafka for your messaging, Zookeeper for service management, Spark for Data Science, the list goes on.  Even my favorite language, Elixir, is built with distributed systems in mind.  But there’s a catch

Continue reading

Advent of Code 2016 Day 15 (Typescript)

Advent of Code 2016 Day 14 (Go)
Advent of Code 2016 Day 13 (Lua)
Advent of Code 2016 Day 12 (C#)
Advent of Code 2016 Day 11 (Groovy)

Advent of Code 2016 Day 10 (OcaML)

Advent of Code 2016 Day 9 (Factor)

Advent of Code 2016 Day 8 (c++)
Advent of Code 2016 Day 7 (Javascript)
Advent of Code 2016 – Day 6 (Julia)
Advent of Code 2016 – Day 5( Java 8)

Advent of Code 2016 – Day 4 (Perl 6)

Advent of Code 2016 – Day 3 (Clojure)
Advent of Code – Day 2 (Python 3)
Advent Of Code 2016 – Day 1(Haskell)

Day 15

Start: 12/20/2016

Finish 12/20/2016

Language: Typescript

SPOILER ALERT: If you have any inkling, any whatsoever, to work on the Advent of Code…. DO NOT READ THIS BLOG POST.  DO NOT LOOK AT MY GITHUB PROJECT.  It is no fun if you’re not solving it yourself, and you’ll feel so much better about yourself if you can figure it out without looking up an answer.  This blog post is not to give away the answer, but instead, is there for people to learn from.

As always, the following code is in my GitHub: https://github.com/pviafore/AdventOfCode2016

The Challenge

 

I’m not sure how to describe this challenge, as it was a bunch of math calculations to see when a bunch of interacting circles were in a specific position.   It’s probably best if you go check out the problem yourself, as I really can’t describe it well. 

I decided to try out Typescript on this one.  I prefer static typing, and I want to get better at some languages that compile to Javascript.

Part 1

 

This only took  me 40 lines of TypeScript, so that was real nice.  I think I found a pretty cool solution for taking care of this, and I got to learn about ECMAScript2015 generators along the way.

interface Disc {
   totalPositions: number,
   initialPosition: number,
}

function* infiniteSequence(){
  var index = 0;
  while(true)
    yield index++;
}

function* filter(iterable:IterableIterator, f:(number)=>boolean){
    for(let item of iterable){
        if(f(item)){
            yield item
        }
    }
}

function toDisc(str:string): Disc {
    const regex:RegExp = /Disc #\d has (\d+) positions; at time=0, it is at position (\d+)./
    const matches = str.match(regex);
    return {totalPositions: parseInt(matches[1], 10), initialPosition: parseInt(matches[2], 10)}
}

function isTimeAllowed(num: number, disc:Disc)
{
    return ((num + disc.initialPosition) % disc.totalPositions) == 0;
}

function getAllowedPositions(iterable:IterableIterator, disc:Disc, discNumber:number ){
    return filter(iterable, num => isTimeAllowed(num + discNumber + 1, disc));
}

declare function require(name:string);
const fs = require("fs");
const lines = fs.readFileSync("day15.txt", "utf8").split("\n");
const discs = lines.filter(s => s !== "").map(toDisc);
const allowedNumbers = discs.reduce(getAllowedPositions, infiniteSequence());
console.log(allowedNumbers.next().value);

I’m going to skip over the Disc interface, as it just kept up with the initial position and total number of positions.  Converting from a string to a disc was easy too, as I had the use of a regex to help me out.
So, how I tried to tackle this solution was to start with an infinite sequence of integers to represent my time domain.  I also provided a way to filter out values I didn’t want.

function* infiniteSequence(){
  var index = 0;
  while(true)
    yield index++;
}

function* filter(iterable:IterableIterator, f:(number)=>boolean){
    for(let item of iterable){
        if(f(item)){
            yield item
        }
    }
}
Then, I wanted to reduce each disc against that time series,  continuing to apply a filter function on it to make sure that only that disc’s positions would match up at that time. This meant that I was using the composition of all the discs at once to determine which allowedNumbers I could use.

const allowedNumbers = discs.reduce(getAllowedPositions, infiniteSequence());
console.log(allowedNumbers.next().value);
I calculate if a disk is allowed by taking the discNumber, adding my current time and adding 1.  I add the discNumber since it takes a second to reach each disc, and add 1 since the disc numbers are zero-based and I need them one-based.  Then I add the initial position in and make sure that my modulus of the total positions is zero (meaning I can accept a ball.


function isTimeAllowed(num: number, disc:Disc)
{
    return ((num + disc.initialPosition) % disc.totalPositions) == 0;
}

function getAllowedPositions(iterable:IterableIterator, disc:Disc, discNumber:number ){
    return filter(iterable, num => isTimeAllowed(num + discNumber + 1, disc));
}

Part 2

Another real easy one, as I just had to enter in another line of input to my text file and my code still worked.

 

Wrap-up

I give myself an A- for this one.  Typescript was fun; I prefer static typing and it was still Javascript that I was familiar with.  I didn’t dive deep enough to really understand what else Typescript can buy me, so that’s why its not a straight up A.  I really liked my solution too, as I got to deal with infinite sequences and reducing filter functions over them.

 

Next up is Scala for Day 16.  Back to the JVM for that one.  See you then.