adventofcode

Happy Advent 2020! Please put answers in the pinned threads or create one if it does not exist yet. | https://github.com/adventofcode-clojurians/adventofcode-clojurians | Join the private leaderboard with code 217019-4a55b8eb
pesterhazy 2018-12-02T00:01:56.164700Z

I think the "rule" that predicates should return booleans is a bit silly

pesterhazy 2018-12-02T00:02:46.165100Z

There nothing wrong with truthiness

mfikes 2018-12-02T00:05:19.165500Z

I like how Dan Dorman's solution uses a transient that is eventually discarded (no persistent! needed to derive value from the transient). https://github.com/dandorman/advent-of-code-2018/blob/master/src/aoc2018/d01.cljc#L18

danielgrosse 2018-12-02T21:46:18.334Z

Amazing how this speeds up the calculation. I had the solution without transient and it took my mac around 10 minutes to get the result. With Dormans one it had no calculation time at all.

lilactown 2018-12-02T00:10:50.166200Z

oh that input->vec is also very nicely clever

mfikes 2018-12-02T00:11:14.167100Z

Oh wow. Nice hack.

lilactown 2018-12-02T00:11:37.167700Z

wish I had thought of that. I didn’t even think to reach for the reader like the rest of ya’ll; I pieced together a solution using Integer/parseInt

pesterhazy 2018-12-02T00:16:13.167900Z

@lilactown same here

dpsutton 2018-12-02T00:17:31.168800Z

i prefer traditional parsing steps. more like real life. I would never ship production code that calls read on input like that. i also don't like when the language makes some things more easy like that

dpsutton 2018-12-02T00:17:59.169400Z

like when the syntax they pick happens to align with literals in the language you are using. unless you make a language like that a la racket

taylor 2018-12-02T00:20:42.170600Z

I think Rich himself strayed from this guideline for at least one predicate in spec

lilactown 2018-12-02T00:25:44.171200Z

true. It just ate up about 80% of the time of part 1 for me :P

lilactown 2018-12-02T00:25:56.171600Z

gotta get those leaderboard spots!

mfikes 2018-12-02T00:32:23.172300Z

Oh, come on, how often do you get to do something like

(eval (read-string (str "(apply + [" input "])")))
😜

mfikes 2018-12-02T00:34:38.173500Z

Shia LaBeouf / Chuck Norris, style programming

vijaykiran 2018-12-02T00:34:49.173900Z

🙂 That’s pretty much what I did 😄

ihabunek 2018-12-02T00:34:55.174Z

here's a solution in grep for one task in 2015 https://github.com/ihabunek/aoc2015-elixir/blob/master/src/day16.sh 🙂

mfikes 2018-12-02T00:35:41.174400Z

Hah

vijaykiran 2018-12-02T00:35:45.174600Z

(eval (read-string 
          (str "(+ " input ")")))

mfikes 2018-12-02T00:36:07.175700Z

"This solution does not require programming." Just pure thought.

borkdude 2018-12-02T00:36:19.176200Z

I didn’t know Integer/parseInt and js/parseInt both accept +1 and -1, else I would have used that instead of read-string

mfikes 2018-12-02T00:37:40.177300Z

To put things in perspective, when I mentioned this problem to my 15-yo, he first said he would take the absolute value of each, but remember the sign, so you would know whether to add or subtract the absolute value.

dpsutton 2018-12-02T00:39:57.178300Z

that's where i went at first. they just happened to encode the data in a convenient literal

mfikes 2018-12-02T00:40:06.178700Z

Cool, I was getting a stack overflow on my input size for this.... wondering why.

lilactown 2018-12-02T00:45:15.179800Z

I decided to try parseInt +5 first, but if it hadn’t worked I was planning on just removing all +’s before parsing

☝️ 1
2018-12-02T00:45:27.180100Z

same^

mfikes 2018-12-02T00:45:51.180600Z

I forgot to even look for + in the input, and just proceeded Leroy Jenkins-style.

2018-12-02T00:46:55.180900Z

https://i.imgur.com/3L9vyNi.gif

mfikes 2018-12-02T00:47:17.181200Z

Yesss

mfikes 2018-12-02T00:47:29.181400Z

The way most code is written.

2018-12-02T00:47:46.181700Z

:truestory:

2018-12-02T00:47:56.181900Z

omg… the waste!

mfikes 2018-12-02T00:47:57.182100Z

Unless the hammock calls.

2018-12-02T00:48:30.182200Z

just | into a single grep process!

2018-12-02T00:48:40.182400Z

sry — I’m a bash dev by training 😛

lilactown 2018-12-02T00:50:36.183600Z

I recently bought an iPad so that I could still computer without being near a dev workstation, so that I would spend less time writing code and more time hammocking

lilactown 2018-12-02T00:51:11.184500Z

that went OK until I figured out how to setup ssh / emacs / tmux 🤪

rmprescott 2018-12-02T18:42:55.266700Z

I probably shouldn't mention http://repl.it then... ;D

lilactown 2018-12-02T18:59:15.268100Z

😱

rmprescott 2018-12-02T19:07:58.273400Z

My mac is in the shop so I'm working there: https://repl.it/@RalphPrescott/AoC-2018

mfikes 2018-12-02T00:51:44.185200Z

The difficulty of entering forms into Replete gives you plenty of time to think if you go that route.

lilactown 2018-12-02T00:52:21.185700Z

haha. I did mess with replete. it’s pretty impressive!

lilactown 2018-12-02T00:53:01.186400Z

I threw up an issue about being able to save to disk or gist :P I know it’s just a wish-list thing

👍 1
mfikes 2018-12-02T00:57:39.187400Z

I'm curious what fraction of the solutions fail to handle the "back to 0" case. (For input [+1 -1], for example)

uosl 2018-12-02T12:38:05.219800Z

Mine did until I started adding tests. At that moment I realized why your solution had consed the reductions onto 0 😛 Although passing 0 as init to reductions worked for me.

taylor 2018-12-02T01:14:52.187500Z

is the correct answer 1 for that input?

dpsutton 2018-12-02T01:16:43.187700Z

depends if you consider a sequence of 0 elements having a sum of 0, then the sequence of 2 elements would have a sum of 0. or most likely the sequence of [1] an then [1 -1 1] having sums of 1 is what they most likely mean

taylor 2018-12-02T01:17:43.187900Z

oh, I’m thinking specifically about part 2

dpsutton 2018-12-02T01:18:11.188100Z

well that's what i'm talking about as well. there are arguments for 0 or 1

taylor 2018-12-02T01:20:41.188300Z

ohh I see now, one argument is that the starting frequency of 0 should be considered when looking for the first duplicate

taylor 2018-12-02T01:21:23.188500Z

in that case, my solution fails 🙂

taylor 2018-12-02T01:21:39.188700Z

>+1, -1 first reaches 0 twice.

taylor 2018-12-02T01:23:15.188900Z

but I suppose I can just start with #{0} instead of #{} and handle that

dpsutton 2018-12-02T01:24:10.189100Z

it's easy to miss this subtlety. not sure which way to fall but i guess good to be conscious of which one you think is the right answer rather than whatever your reduce expression returns

taylor 2018-12-02T01:25:11.189300Z

the AoC test cases seem to indicate the answer should be 0

dpsutton 2018-12-02T01:38:37.189500Z

Which test case?

lilactown 2018-12-02T01:40:53.190200Z

It's written in the description of the puzzle

☝️ 1
2018-12-02T03:36:58.192200Z

I hope I'm not the only one who smashed the stack trying part 2 😞

Mario C. 2018-12-02T04:58:01.192500Z

2 mins gentlemen 😛

2018-12-02T05:20:45.192900Z

sad, rank 757

pesterhazy 2018-12-02T10:40:02.213700Z

very clever

bhauman 2018-12-02T15:48:18.239600Z

thats fun 🙂

dpsutton 2018-12-02T06:52:01.193900Z

Ah. The day 1 first duplicate is clever

dpsutton 2018-12-02T06:52:15.194200Z

I didn't think of deleting and checking

mfikes 2018-12-02T06:53:47.194600Z

This problem will lead to a richer variation of solutions. 🙂

dpsutton 2018-12-02T06:54:40.196Z

I just realized mine is not funny general. I compare them to their neighbors after sorting. But there is no reason the single difference would not move their position in the sorted list

dpsutton 2018-12-02T06:54:52.196400Z

Funny = fully

dpsutton 2018-12-02T06:56:19.197300Z

Although now I can't think of a better approach than your brute force

ClashTheBunny 2018-12-02T07:01:34.198200Z

Day 2 https://gitlab.com/randall.mason/advent-of-code/blob/master/src/advent_of_code_2018/day02.clj Happy about some of it, other parts seem like they could be MUCH better. Perfomance is fine.

dpsutton 2018-12-02T07:06:24.199400Z

You can drop the first two comparisons in your levenshtein since all the strings are either equal or replaced. There are no deletions or additions to worry about

dpsutton 2018-12-02T07:07:26.199900Z

Ah ok you use simple cost only :)

Mario C. 2018-12-02T07:16:33.201100Z

Day 2 part 1 took me 2 hours to do ooof.. Can't come up with a solution for part 2, too tired >.<

orestis 2018-12-02T07:21:18.202600Z

Woof, I solved day2 part2 but mfikes has already contributed his data to advent-of-cljc. How do I submit a patch instead of a PR to Github? 🤪

orestis 2018-12-02T07:28:56.203500Z

Day2: https://github.com/orestis/advent-of-cljc/blob/master/src/aoc/y2018/d02/orestis.cljc — I need to finally figure out how to get a CLJS REPL setup so I can see why the CLJS tests are failing. Most likely something to do with chars/ints etc.

orestis 2018-12-02T07:44:37.203700Z

So in part2, instead of considering one string against all others, repeating, you are dropping the first character, search for duplicate, second character, search for duplicates etc? Neat!

dpsutton 2018-12-02T08:02:24.204600Z

I'm interested to see different approaches that are sound. Mine was probabilistic

helios 2018-12-02T08:18:11.205900Z

here's mine: https://github.com/Heliosmaster/advent-of-code-2018/blob/master/src/adventofcode_2018/day2.clj but i liked @mfikes answer a bit more 😉 there are some functions (like keep) that I have used rarely so I tend to forget about them 😄

borkdude 2018-12-02T08:21:29.207100Z

@orestis about failing CLJS-tests: if you change the deftest to clojure.test/deftest you will see the error. I’m not sure why it’s not showing right now. I wrapped the deftest body in time to see the performance. PR welcome that fixes this

orestis 2018-12-02T08:22:44.208Z

In the end cider can happily jack in to a CLJS REPL for me so I fixed my code interactively.

2018-12-02T09:43:57.209200Z

@borkdude I've invited a few more people as collaborators to help with merging pr's

borkdude 2018-12-02T10:15:15.209600Z

@thegeez thanks

pesterhazy 2018-12-02T10:28:41.210Z

My solution to Day 2: https://github.com/pesterhazy/advent2018/blob/master/src/advent/puzzle02.clj#L60

borkdude 2018-12-02T10:30:05.210700Z

4 solutions in advent-of-cljc so far: https://github.com/borkdude/advent-of-cljc/tree/master/src/aoc/y2018/d02

pesterhazy 2018-12-02T10:30:48.211400Z

This time I spent most of my time on setting up rebel-readline, and on writing a lazy pairs function

borkdude 2018-12-02T10:31:27.212Z

I didn’t try to write clever code, just did the most straightforward thing to get to the solution fast, because I had a coffee meeting coming up

pesterhazy 2018-12-02T10:31:43.212200Z

No excuses!! 🙂

borkdude 2018-12-02T10:33:55.213600Z

haha 🙂

pesterhazy 2018-12-02T10:42:35.214300Z

is there a cutoff time when you need to submit solutions? https://clojurians.slack.com/archives/C0GLTDB2T/p1543726681192500

orestis 2018-12-02T11:58:01.214900Z

No, not at all. You could do these next year.

2018-12-02T12:09:47.216Z

https://github.com/kfirmanty/advent-of-code-2018/blob/master/src/advent_of_code_2018/day2.clj my solution is also rather not optimized, but it might be fun to look back after few days and try to create most performant solution (but probably with lesser readibility)

2018-12-02T12:11:41.216200Z

I especially have a feeling that there is a simpler way to do: (defn without-diff [id1 id2] (apply str (map #(when (= %1 %2) %1) id1 id2))) so I will check other solutions 😉

gklijs 2018-12-02T12:28:46.219100Z

Anyone hooked in something like https://github.com/gobanos/cargo-aoc I got jmh setup for Java now, would be nice to compare results. I don't know if I have the time, but otherwise I might setup a project, comparing several solutions.

helios 2018-12-02T12:29:44.219600Z

@pesterhazy the countdown was for the new puzzle release 🙂

borkdude 2018-12-02T12:38:16.220200Z

@gklijs are you aware of https://github.com/borkdude/advent-of-cljc or is that a different thing?

gklijs 2018-12-02T12:39:13.221100Z

I know it's there and like to look at the solutions, but don't know if there is some performance measure there?

borkdude 2018-12-02T12:39:54.221600Z

if you go to the CircleCI icon, open a build and then look at the tests, you will see something like that

gklijs 2018-12-02T12:40:01.221800Z

ok

borkdude 2018-12-02T12:40:49.222300Z

not anything fancy, just time, not criterion

gklijs 2018-12-02T12:40:51.222700Z

found them

borkdude 2018-12-02T12:41:02.222900Z

but it would be trivial to hook that up. I’m only concerned about the time to build

gklijs 2018-12-02T12:43:34.224800Z

You don't want it in your build, it takes really long. I now have a separate profile to run them, just putting the result back with the method and then remove the annotation in java, so I can easily run the other ones.

borkdude 2018-12-02T12:44:35.226400Z

you could make a branch, replace the time call with criterium quickbench, push the branch and watch the build. if we don’t merge it to master, it should be fine.

benoit 2018-12-02T12:47:08.229400Z

Very clever solution from @mfikes. It ismy first advent-of-code. Do the solutions often build on previous days's solutions? Do we build up code for 23 days to make writing the solution on the 24 a bit easier?

gklijs 2018-12-02T12:48:54.230600Z

Can of related to that I often struggle with how generic a solution should be, for my java colleagues I also see them putting some effort in nicely handling edge cases.

gklijs 2018-12-02T12:49:38.231200Z

Default settings, at least in java take about 15 minutes for each method.

2018-12-02T13:17:15.231600Z

If I remember correctly in 2017 there was once a day to built upon solution of previous day but I think it was a exception to the rule

gklijs 2018-12-02T13:19:32.231800Z

the @mfikes solution is also very fast compared to the others

Testing aoc.y2018.d02.borkdude
part-2 took 54.986879 msecs
part-1 took 0.38845 msecs

Testing aoc.y2018.d02.dfuenzalida
part-2 took 126.335371 msecs
part-1 took 5.086755 msecs

Testing aoc.y2018.d02.mfikes
part-2 took 4.250777 msecs
part-1 took 7.145989 msecs

Testing aoc.y2018.d02.mrmcc3
part-2 took 82.483809 msecs
part-1 took 4.544113 msecs

Testing aoc.y2018.d02.orestis
part-2 took 103.404907 msecs
part-1 took 8.286482 msecs

mfikes 2018-12-02T13:23:39.232600Z

Hmm. I didn’t write it with speed in mind.

mfikes 2018-12-02T13:25:25.234700Z

I actually wonder if day 2 had day 1 in mind… in this case there was the concept of “sameness / duplication” in both problems.

gklijs 2018-12-02T13:31:38.234900Z

no, I was also surprised, gonna use it in my javaRx now, and compare to me previous solution.

mfikes 2018-12-02T13:53:47.235100Z

On the surface, when count is applied to filter vs. keep, you essentially get the same result for this problem. So you might wonder why I was using keep... it was because the intermediate output in the REPL looked a little simpler, that's all.

benoit 2018-12-02T14:04:31.235300Z

ok, thanks.

gklijs 2018-12-02T14:47:14.235500Z

Turned out to be slightly faster than the previous solution, 3.445 msecs on a warmed up vm

taylor 2018-12-02T15:02:07.237700Z

day 2 was fun. I feel like there’ll be more variety in the solutions, here’s mine https://github.com/taylorwood/advent-of-code/blob/master/src/advent_of_code/2018/2.clj

bhauman 2018-12-02T15:45:55.238400Z

just finished

bhauman 2018-12-02T15:46:32.239500Z

now to look at the other answers 🙂

dpsutton 2018-12-02T15:50:16.240100Z

So it seems brute Force is the only strategy?

bhauman 2018-12-02T16:00:43.242300Z

for the most part one way or the other you are going to have to compare until you find

bhauman 2018-12-02T16:01:26.242400Z

one interesting thing is that sorting the list may increase the likelyhood that the search ends sooner

bhauman 2018-12-02T16:02:11.242600Z

as you normally generate combinations from the original order

bhauman 2018-12-02T16:06:07.242800Z

actually this is not true for my data it increased the number of cycles quite a bit

bhauman 2018-12-02T16:20:37.246200Z

actually a tree search would probably provide the best performance

bhauman 2018-12-02T16:21:19.246600Z

as you are eliminating prior comparisons

mfikes 2018-12-02T17:16:04.250400Z

It is possible to parallelize the search. For the algorithm I'm using, the problem is essentially linear in the input, but with it doing a linear search over each character position, one at a time. The answer happens to be at position 20 for my input data. Those searches per character position can be done in parallel. The problem size isn't really big enough to benefit greatly from this, but it can cut it down from 3 ms to 1.5 ms. https://gist.github.com/mfikes/d2cf0c9de3808564f7b039f10635ede4#file-parallel-clj-L34-L44

bhauman 2018-12-02T17:22:34.251Z

my tree solution is 7ms

bhauman 2018-12-02T17:22:54.251500Z

compared to lazy search of 99ms

bhauman 2018-12-02T17:25:25.253Z

the tree search intelligently eliminates large swaths of search area

bhauman 2018-12-02T17:39:28.254100Z

@mfikes ^

gklijs 2018-12-02T17:40:30.255300Z

Is that with warm up? Rust is doing around 0.25 ms for each of day two

bhauman 2018-12-02T17:40:38.255500Z

lol

bhauman 2018-12-02T17:41:30.256600Z

of course it is

gklijs 2018-12-02T17:47:39.261200Z

With RxJava it's about 3/6 ms, measured with jmh. I'm still kind of figuring out what I like best/want to get better in.

taylor 2018-12-02T17:48:27.261800Z

Very cool. Gonna need to study this for a while :face_with_monocle:

andrew.sinclair 2018-12-02T18:12:59.263800Z

Hi all! I love this time of year! My solutions aim for leaderboard points rather than elegance and best practices. It’s great to see all the unique ways other clojurians come up with!

andrew.sinclair 2018-12-02T18:13:18.264Z

https://github.com/AndrewSinclair/aoc-2018

vijaykiran 2018-12-02T18:17:29.264500Z

My day2-one has more lines than day2-two https://github.com/vijaykiran/aoc-2018/blob/master/src/aoc_2018/two.clj#L279 🙂

dpsutton 2018-12-02T18:18:13.265500Z

@bhauman i was reading your tree search and it prunes a bit too heavily (search ["abc" "ddd" "zbc" "ahg" "zzz"]) should match abc/zbc => "bc" but it fails to find them

vijaykiran 2018-12-02T18:38:57.266500Z

Are these from CI ?

part-1 "Elapsed time: 5.87954 msecs"
part-2 "Elapsed time: 0.829347 msecs"
These are mine from (time …) < it is super-ugly-code though

bhauman 2018-12-02T18:55:16.267400Z

@dpsutton oh cool thanks, I think thats a base case lemme check it out

bhauman 2018-12-02T18:57:12.267700Z

oh I broke it when I refactored

lilactown 2018-12-02T19:00:04.269600Z

> TFW you accidentally leave that println inside the inner loop of your solution and you run it on your real input 🤦

lilactown 2018-12-02T19:01:15.271200Z

at least in CIDER/Emacs outputting that much text to a buffer wrecks me

rmprescott 2018-12-02T19:02:01.271600Z

Tempted to ask this on another channel - but it's also some hints on the first few problems. Are there any more idiomatic approaches to these short helpers?

rmprescott 2018-12-02T19:03:53.271700Z

bhauman 2018-12-02T19:04:16.272200Z

@dpsutton nope its just wrong 🙂

dpsutton 2018-12-02T19:04:39.272500Z

Mine too :)

dpsutton 2018-12-02T19:05:27.272900Z

a sort and compare with neighbor works on the input but is not right in general. (i realized after doing that)

bhauman 2018-12-02T19:13:17.274100Z

I found the problem but of course it slows it down 🙂

dpsutton 2018-12-02T19:13:35.274500Z

yes you have to be more cautious of when you can prune things

dpsutton 2018-12-02T19:14:56.274800Z

is it instead of apply intersection you look for duplicates?

gklijs 2018-12-02T19:15:41.275400Z

The list is from CI, the 3,445 is from jmh benching.

bhauman 2018-12-02T19:15:46.275600Z

right now I’m intersecting two by two

dpsutton 2018-12-02T19:16:01.276100Z

i was mulling that idea just now

bhauman 2018-12-02T19:16:13.276700Z

which is searching for duplicates

dpsutton 2018-12-02T19:16:15.276800Z

look for things with the first two characters have non-empty intersection

lilactown 2018-12-02T19:16:44.277600Z

oof, ya’ll are making me feel bad. my day2 part2 solution is ~600ms 😆

vijaykiran 2018-12-02T19:16:59.277900Z

okay! I only ran (time ..)

bhauman 2018-12-02T19:17:26.278500Z

I’m thinking that its better to do this as a tree as well

vijaykiran 2018-12-02T19:17:26.278600Z

As long as it works 🙂 We are not in a hurry

vijaykiran 2018-12-02T19:17:38.278800Z

@lilactown ^

😛 1
dpsutton 2018-12-02T19:18:12.279400Z

@lilactown but the "fast" versions we are talking about are unsound 🙂 slow and steady

lilactown 2018-12-02T19:18:52.279800Z

still, going fast is fun!

vijaykiran 2018-12-02T19:19:07.280100Z

Hey - my version is fast and it is very sound (as in very noisy) 😄

gklijs 2018-12-02T19:19:47.280500Z

I have something similar in Java now, and the rust create also has it, will be adding some CI config to get some numbers there

vijaykiran 2018-12-02T19:20:11.281300Z

For the second one, I was even considering not writing code and Cmd+F and eye-ball the similar strings

rmprescott 2018-12-02T19:21:14.282300Z

@bhauman - i'm missing something. I don't see how you can do this other than pairwise. What would you use as the comparison in your tree?

rmprescott 2018-12-02T19:22:00.283100Z

I can't think of anything that (properly) constrains the solution space.

bhauman 2018-12-02T19:22:55.283700Z

hold on committing

bhauman 2018-12-02T19:25:08.284900Z

in this solution I’m doing a depth first search

bhauman 2018-12-02T19:25:28.285200Z

so it should eliminate comparisons

bhauman 2018-12-02T19:26:05.285700Z

its takes a third of the amount of time as my straight forward solution

bhauman 2018-12-02T19:27:17.286400Z

now breadth first search would really be interesting

bhauman 2018-12-02T19:27:22.286600Z

as well

bhauman 2018-12-02T19:27:41.287Z

@dpsutton mines updated

bhauman 2018-12-02T19:59:49.288700Z

and updated again with comments

mfikes 2018-12-02T20:01:04.290Z

IIRC, we will probably see a few perf-critical ones in a couple weeks (where your algorithm is important if you want it to complete in a few minutes)

💯 1
☝️ 1
mfikes 2018-12-02T20:01:49.290400Z

Or within the RAM you have 🙂

lilactown 2018-12-02T20:03:24.292200Z

answer: just throw a naive solution at a cluster and come back the next day 😛

lilactown 2018-12-02T20:03:36.292500Z

slow and steady!

pesterhazy 2018-12-02T20:03:50.293Z

surely @mfikes's solution must be the fastest no?

mfikes 2018-12-02T20:04:09.293500Z

Oddly, mine wasn't at all meant to be fast. It got lucky.

uosl 2018-12-02T20:04:11.293600Z

was there a problem like that last year? it does say this in the about page: >every problem has a solution that completes in at most 15 seconds on ten-year-old hardware.

uosl 2018-12-02T20:05:49.295Z

although my first attempt at day 1 part 2 would have taken at least 15 minutes to finish :rolling_on_the_floor_laughing:

pesterhazy 2018-12-02T20:05:55.295300Z

my super-inefficient solution completes in 47ms

mfikes 2018-12-02T20:05:56.295500Z

There was that one with the particle simulation that was a real PITA, where you had to almost eyball the solution.

mfikes 2018-12-02T20:06:13.295800Z

Day 20 last year.

uosl 2018-12-02T20:07:16.296200Z

ooo. this is my first year so looking forward to any problems that places me in a rut

mfikes 2018-12-02T20:08:13.297800Z

IIRC, one pattern is where part 1 can be done with a naive algorithm, and then Wastl asks you to do it for a problem with a billion iterations in part 2.

2018-12-02T20:08:26.298100Z

yep^

pesterhazy 2018-12-02T20:08:35.298400Z

It's my first year as well. What will Day 3 bring? More duplicate detection? 🙂

bhauman 2018-12-02T20:10:40.299400Z

@vijaykiran try [“abc” “ddd” “zbc” “ahg” “zzz”]

bhauman 2018-12-02T20:10:50.299700Z

your solution fails for me on that

Mario C. 2018-12-02T20:11:45.300700Z

wow part 2 was pretty cumbersome my solution was kinda hacky but it got the job done 😛 https://github.com/HeyItsMario/AdventOfCode2018/tree/master/day2

lilactown 2018-12-02T20:12:15.301200Z

let’s see. last year’s day 1 was pretty similar (summing things). day 2 was doing some integer math (finding min/max, divisors)

dpsutton 2018-12-02T20:13:27.301700Z

yeah. and then you start trying to code generically for part 1 and then you don't get to reuse any for part 2 sometimes

lilactown 2018-12-02T20:14:18.302800Z

there were a few times last year where if you solved part 1 a certain way, part 2 fell out of it quite nicely

lilactown 2018-12-02T20:14:32.303200Z

but most of the time I spent trying to make part 1 “generic” without knowing part 2 was a waste, yes

mfikes 2018-12-02T20:18:53.304300Z

Day 16 was of last year was an example of naive part 1 could in theory solve part 2, but it involved a dance of some sort that went out a billion iterations

2018-12-02T20:34:53.304700Z

@gklijs I’d love to see your Rust/RxJava example

vijaykiran 2018-12-02T20:34:54.304900Z

sorted stuff breaks it - I made some assumptions after sorting my puzzle input

2018-12-02T20:35:09.305400Z

did you do any optimizations or is it basically brute force?

2018-12-02T20:40:46.309700Z

I can’t get my brute force below ~130ms or so

gklijs 2018-12-02T20:40:46.309800Z

I did do the mfikes trick, but that didn't do much to performance, did lose half the needed code. In Rust I'm really inexperienced, so need to google for a lot of stuff,and just happy when it runs. But I figure especially the second one really does well, since it's just moving pointers around. Code at https://github.com/gklijs/advent_of_code_2018 'Gerard' is RxJava, 'Rust/oac_2018' is rust, the other folder are Java from colleagues.

gklijs 2018-12-02T20:42:02.310700Z

It could also be your problem is harder, that's the nice thing about https://github.com/borkdude/advent-of-cljc they all use the same data

2018-12-02T20:42:52.311100Z

ah, didn’t even consider that

2018-12-02T20:43:00.311400Z

I mean… also just hardware

gklijs 2018-12-02T20:45:59.312400Z

It's the first year for me, and also for the company, maybe next year I set something up with GraalVM

2018-12-02T20:48:15.312800Z

the mfikes trick (w/ transducers) gets me down to ~2ms

2018-12-02T20:49:38.313400Z

actually… holy hara

2018-12-02T20:50:24.314700Z

for early puzzles I just write really long oneliners in a repl, they tend to be convoluted and slow 😂

➕ 1
2018-12-02T20:50:37.314900Z

(str (subs s 0 i)
     (subs s (inc i)))
^is WAY faster than
(.toString (.deleteCharAt (StringBuilder. s) i))

2018-12-02T20:51:04.315300Z

down to .5ms

mfikes 2018-12-02T21:01:48.315700Z

Reflection?

2018-12-02T21:05:20.316400Z

I hinted the constructor

2018-12-02T21:05:23.316700Z

in my timing

pesterhazy 2018-12-02T21:06:03.317300Z

@nooga I'm the same way, whatever I can possibly squeeze into a one-liner in the repl

2018-12-02T21:07:13.318600Z

@mfikes that was it

pesterhazy 2018-12-02T21:07:24.319Z

only roadblock: rebel-readline, as great as it is, doesn't submit when I hit Return while the cursor is not at the end of the line

1
2018-12-02T21:07:48.319300Z

(fn [^String s]
  (.toString (.deleteCharAt (StringBuilder. s)
                            ^Long i))
is comparable

mfikes 2018-12-02T21:09:35.319700Z

So, transducers got it down to half a millisecond. Nice.

mfikes 2018-12-02T21:09:50.320Z

Rust speed within reach. 🙂

bhauman 2018-12-02T21:11:33.321Z

@pesterhazy ctrl-x ctrl-m

mfikes 2018-12-02T21:11:52.321600Z

Hah! Every time that happens on Apropos, we shout out Bruuuucee!

mfikes 2018-12-02T21:12:03.321900Z

Now we know they way 🙂

2018-12-02T21:12:15.322300Z

Bad news…

2018-12-02T21:12:24.322500Z

My .5ms was bugged

2018-12-02T21:12:27.322700Z

2.1ms

mfikes 2018-12-02T21:12:37.323Z

Damn. 👿

2018-12-02T21:12:39.323200Z

ikr

slipset 2018-12-02T21:14:42.323600Z

ah, spent way too much time on part two of day two.

mfikes 2018-12-02T21:15:47.324200Z

IMHO, day 2 part 2 was a bit harder than you would expect, so early on

pesterhazy 2018-12-02T21:16:35.324500Z

@bhauman wow, thanks

slipset 2018-12-02T21:17:40.324900Z

I was over complicating things a bit.

slipset 2018-12-02T21:22:04.325400Z

I’m probably not so concerned with speed 🙂

slipset 2018-12-02T21:23:51.326600Z

Don’t want to spoil anything 🙂

pesterhazy 2018-12-02T21:26:28.327400Z

@bhauman is there any way to bind the Enter key to clojure-force-accept-line rather than accept-line?

pesterhazy 2018-12-02T21:26:42.327900Z

I tried

cat ~/.clojure/rebel_readline.edn
{:key-bindings { :emacs [["RETURN" :clojure-force-accept-line]] }}

pesterhazy 2018-12-02T21:27:07.328600Z

I can bind ^J, which is nice, but a real Enter/Return would be better

bhauman 2018-12-02T21:27:36.329400Z

^J or ^m I think

pesterhazy 2018-12-02T21:27:39.329600Z

wait! this works

pesterhazy 2018-12-02T21:27:41.329900Z

{:key-bindings { :emacs [["^M" :clojure-force-accept-line]] }}

bhauman 2018-12-02T21:27:53.330400Z

yes control M is a real return

pesterhazy 2018-12-02T21:28:02.330600Z

it's always just after bothering someone that you find the answer yourself

bhauman 2018-12-02T21:28:21.331300Z

so the thing is that you don’t get multiline that way

pesterhazy 2018-12-02T21:28:41.331700Z

yeah maybe I can bind that to ^j

pesterhazy 2018-12-02T21:29:10.332500Z

honestly I don't often write multiple lines except by mistake

pesterhazy 2018-12-02T21:30:46.333Z

yeah, ^j is bound to accept-line by default - that works well for me

pesterhazy 2018-12-02T21:33:58.333800Z

now it's perfect 🎉

🤘 1
borkdude 2018-12-02T21:57:57.334600Z

Day 2 for Advent of CLJC:

Testing aoc.y2018.d02.borkdude
part-2 took 47.616232 msecs
part-1 took 0.408357 msecs

Testing aoc.y2018.d02.dfuenzalida
part-2 took 118.803809 msecs
part-1 took 5.012151 msecs

Testing aoc.y2018.d02.iamdrowsy
part-2 took 362.461886 msecs
part-1 took 4.806461 msecs

Testing aoc.y2018.d02.mfikes
part-2 took 4.994811 msecs
part-1 took 7.194342 msecs

Testing aoc.y2018.d02.mrmcc3
part-2 took 92.999763 msecs
part-1 took 5.206182 msecs

Testing aoc.y2018.d02.orestis
part-2 took 98.666185 msecs
part-1 took 8.78663 msecs
https://circleci.com/gh/borkdude/advent-of-cljc/91

borkdude 2018-12-02T21:58:46.335400Z

Good job everyone and thanks for contributing.

borkdude 2018-12-02T22:00:01.336Z

mfikes really nailed it. when I saw his function that deleted one char from a string I was like: oh yeah, of course… 🙂

Mario C. 2018-12-02T22:15:29.336700Z

very humbling seeing y'alls such succinct solutions

2018-12-02T22:37:31.337200Z

(criterium/quick-bench
  (into []
        (comp (keep (fn [i]
                      (first (into []
                                   (comp (map (fn [^String s]
                                                (.toString (.deleteCharAt (StringBuilder. s)
                                                                          ^Long i))))
                                         (dups)
                                         (take 1))
                                   in))))
              (take 1))
        (range (count (first in)))))
Evaluation count : 828 in 6 samples of 138 calls.
             Execution time mean : 702.838769 µs
    Execution time std-deviation : 19.556882 µs
   Execution time lower quantile : 668.965703 µs ( 2.5%)
   Execution time upper quantile : 718.893138 µs (97.5%)
                   Overhead used : 1.830592 ns

2018-12-02T22:38:30.337600Z

where dups is a transducer that emits duplicates

slipset 2018-12-02T23:01:52.338200Z

I wish I understood the reasoning behind @mfikes solution to todays second problem.

mfikes 2018-12-02T23:02:30.338800Z

Maybe I could draw a picture of it

mfikes 2018-12-02T23:04:10.340300Z

I visualize it as first eliminating a column of characters and then seeing if that causes a duplicate to appear in the remaining strings

🎉 1
mfikes 2018-12-02T23:05:59.342Z

abc
axc
def
Eliminate the middle column in that example

👍 1
mfikes 2018-12-02T23:06:17.342400Z

ac then appears twice

slipset 2018-12-02T23:11:00.343Z

Quite cheeky to use yesterdays solution though 🙂

borkdude 2018-12-02T23:15:34.344200Z

he factored out a function that he could re-use: https://github.com/borkdude/advent-of-cljc/commit/17c8f768c75fbb69187eb4ecf892d17612172cdd it could have ended up in some utils namespace as well

fellshard 2018-12-02T23:36:26.345500Z

I'm trying to recreate my solutions in Elixir as a sort of lift-and-shift approach. A lot of common utility between Clojure and Elixir, though the latter is certainly far more verbose and doesn't have quite the same expressiveness for its core lib. Still not bad.

rmprescott 2018-12-02T23:43:23.345800Z

divide and conquer -- nice!

devn 2018-12-02T23:53:19.346400Z

wow, did not think i'd wind up using reductions on problem 1 😄

devn 2018-12-02T23:53:48.347200Z

one of my favorite functions that i keep in my back pocket

👌 1
dpsutton 2018-12-02T23:53:51.347400Z

Reductions and iterate always feel so fancy and sophisticated to me ha

devn 2018-12-02T23:54:10.347700Z

wow, that's actually kind of interesting

devn 2018-12-02T23:54:20.347800Z

i feel like early on when i was using clojure i used iterate a lot

devn 2018-12-02T23:54:25.348300Z

but i don't use it very often these days

devn 2018-12-02T23:54:51.349300Z

like when you mentioned it, i was like "oh right, that exists"

dpsutton 2018-12-02T23:55:17.350300Z

I don't use it very often in our webapp or backend stuff but I like to model solutions to "clever" problems with it

devn 2018-12-02T23:55:53.350800Z

i guess i used it pretty often in 4clojure problems when golfing

devn 2018-12-02T23:56:28.351300Z

and in project euler solutions

devn 2018-12-02T23:56:35.351600Z

which is why i remember it being a "back in the day" kind of thing

dpsutton 2018-12-02T23:57:31.352300Z

That makes sense. It doesn't seem to align with real world things I have to do so it really feels insightful when it works

devn 2018-12-02T23:59:29.353500Z

btw, reductions is "fancy", but i remember using it for a problem where i had a sequence of lines of chat, similar to the way they're presented in slack, so you'd see a nickname, and then you wouldn't see it on any lines they typed immediately after, but i wanted it filled in everywhere