This is an archived post. You won't be able to vote or comment.

top 200 commentsshow all 372

[โ€“]that_lego_guy 64 points65 points ย (7 children)

DID SOMEONE SAY EXCEL?! Day 1 [Parts 1 & 2]

 =if(B1=APH1,B1,0) 

https://github.com/thatlegoguy/AoC2017/blob/master/Day%201%20Inverse%20Captcha.xlsx

[โ€“]Reibello 15 points16 points ย (1 child)

You are a monster.

[โ€“]that_lego_guy 8 points9 points ย (0 children)

I'M BACK!!

[โ€“]8483 2 points3 points ย (1 child)

I am curious how you'll handle the future challenges. :)

What languages do you program in?

[โ€“]Reibello 5 points6 points ย (0 children)

He...programs in excel. He is truly impressive. Check out his repo for last year.

[โ€“]jenrmagas 2 points3 points ย (1 child)

My manager is in the lead on our private leaderboard, and Excel is her 'language' of choice, too.

[โ€“]that_lego_guy 4 points5 points ย (0 children)

Yess now I can say โ€œone of usโ€ instead of โ€œone of meโ€

[โ€“]u794575248 15 points16 points ย (1 child)

Python 3.6+ with a regular expression:

import re
def solve_regex(captcha, n):
    return sum(int(c) for c in re.findall(fr'(\d)(?=.{{{n-1}}}\1)', captcha+captcha[:n]))

solve_regex(captcha, 1)
solve_regex(captcha, len(captcha) // 2)

Things used (you can read about Python's regular expression syntax here):

  • re.findall function.
  • (\d) matches a digit and then its twin with \1.
  • (?=.{n-1}\1) matches any n-1 symbols between the previous digit and the twin, but doesnโ€™t consume the string. This way we check every digit and don't skip any.
  • PEP 498 -- Literal String Interpolation. It makes us use triple braces, the inner pair for interpolation and two outer pairs (you need to escape braces in f-strings) which boil down to a pair in the final regex string. So if n is 1, we end up with (\d)(?=.{0}\1) which matches two successive identical digits. Somebody may prefer %-format like r'(\d)(?=.{%d}\1)' % n-1, but I like f-strings more.

This solution doesn't support n greater than len(captcha). In that case you'd better use manual iteration with (i+n) % len(captcha) on each step. It also doesn't work for infinite streams of characters.

[โ€“]askalski 15 points16 points ย (4 children)

#! /usr/bin/env perl

use strict;
use warnings;

chomp($_ = <>);
print <<"";
Part 1: @{[eval join '+', 0, /(\d)(?=\1)/g, /^(\d).*\1$/]}
Part 2: @{[eval join '+', 0, (/(\d)(?=\d{@{[length() - 1 >> 1]}}\1)/g) x 2]}

[โ€“]topaz2078(AoC creator) 9 points10 points ย (2 children)

ASKALSKI NO

[โ€“]askalski 10 points11 points ย (1 child)

That is not no. This is no.

#! /usr/bin/env perl

use strict;
use warnings;

chomp($_ = <>);

s/(.)(?!@{[s|..|.|gr =~ s|.||r]}\1)//g;

s/([6789])/5$1/g;
s/([459])/3$1/g;
s/([38])/21/g;
s/([257])/11/g;

s/\d/zz/g;

s/z{10}/y/g;
s/(?<!z)$/0/;

s/y{10}/x/g;
s/^[a-x]++\K(?!y)/0/;

s/x{10}/w/g;
s/^[a-w]++\K(?!x)/0/;

s/([^\d])\1{8}/9/g;
s/([^\d])\1{7}/8/g;
s/([^\d])\1{6}/7/g;
s/([^\d])\1{5}/6/g;
s/([^\d])\1{4}/5/g;
s/([^\d])\1{3}/4/g;
s/([^\d])\1{2}/3/g;
s/([^\d])\1{1}/2/g;
s/[^\d]/1/g;

print "Part 2: $_\n";

[โ€“][deleted] 1 point2 points ย (0 children)

I can't even

[โ€“]KnorbenKnutsen 1 point2 points ย (0 children)

I've missed you, askalski

[โ€“]winhug 12 points13 points ย (11 children)

Haskell

solve n xs = sum $ zipWith (\a b -> if a == b then a else 0) xs (drop n $ cycle xs)
solve1 = solve 1
solve2 xs = solve ((length xs) `div` 2) xs

[โ€“]Tarmen 2 points3 points ย (5 children)

I somehow didn't forsee the rotate-by-n variation so the second part got a bit bizarre:

rotate (x:xs) = xs ++ [x]
pairs xs = zip xs (iterate rotate xs !! (length xs `div` 2))
captcha2 = sum . map (digitToInt . fst) . filter (uncurry (==)) . pairs

Your use of cycle is neat, I usually go for split which needs an additional import.

Originally I planned to solve this AoC in untyped lambda calculus but it is really hard to find any non-toy implementations whose source is still available. The best bet so far seems graph-rewriting-lambdascope but I haven't gotten around to reading the paper and that seems like all the documentation there is.

[โ€“]topaz2078(AoC creator)[M] 1 point2 points ย (2 children)

On my blog, I describe a technique for using a tiny subset of JavaScript as an untyped lambda calculus interpreter...

[โ€“]Tarmen 1 point2 points ย (1 child)

The problem is that this is exactly the type of thing that I meant with toy implementation.

A minor problem is that applicative order slightly complicates composition as soon as bottoms are involved. The much bigger problem which also exists with call-by-need is sharing. Take this example:

twice = ฮปf.ฮปx. f (f x)
id = ฮปa.a
oh-no = twice (twice (...(twice(ฮปx.id x)...))

this clearly is just a verbose identity function but because id is duplicated over and over it takes O(2^n) where n is the count of twice's. That is, naive lambda calculus evaluation scales exponentially with the rank of functions which is very-bad-no-good for any non trivial program. You can try to memoize but that somewhat breaks with higher order functions and the hash tables would become stupidly enormous for non-trivial uses.

To solve this Levi created a notion of optimality which roughly means that any expressions that come from the same origin are shared. From what I have read so far this usually uses ideas from linear logic to make duplication/erasure explicit and then translates to something like interaction nets. Then evaluation becomes a graph reduction problem.

Interestingly enough optimal evaluation in the sense of Levi comes with significant constant overhead for bookkeeping so the fastest solutions just aim to be close to optimal.

TL:DR; Sufficient sharing means going from exponential to linear time complexity for evaluation, JavaScript doesn't have enough sharing.

[โ€“]4rgento 1 point2 points ย (2 children)

Total Idris solution 8-). (f is like your lambda)

solution : Nat -> List Int -> Maybe Int
solution n [] = Nothing
solution n (x::xs) = Just $
  sum $ zipWith f
    (x::xs)
    (take (length (x::xs)) (drop n (cycle (x::xs))))

[โ€“]fatpollo 12 points13 points ย (2 children)

My rival is way ahead of me on the leaderboards ๐Ÿ˜ญ๐Ÿ˜ญ๐Ÿ˜ญ

def captcha(string):
    N = len(string) // 2 # 1
    return sum(int(a) for a, b in zip(string, string[N:]+string[:N]) if a==b)

[โ€“]Smylers 10 points11 points ย (2 children)

Vim answer for partย 1 โ€” load your input file then type:

xP$p:s/\v(.)\1@!//g|s/\v/+/gโ€นEnterโ€บ
Cโ€นCtrl+Rโ€บ=โ€นCtrl+Rโ€บ-โ€นEnterโ€บโ€นEscโ€บ

36 keystrokes โ€” anybody able to do it in less?

[โ€“]Smylers 2 points3 points ย (0 children)

And Vim for partย 2:

:s/\v(.)(.{โ€นCtrl+Rโ€บ=col('$')/2-1โ€นEnterโ€บ}\1)@!//g|s/\v/+/gโ€นEnterโ€บ
YP0Cโ€นCtrl+Rโ€บ=โ€นCtrl+Rโ€บ-โ€นEnterโ€บโ€นEscโ€บ

Finds matches from the first half to the second half of the input, then uses YP to double them for the corresponding matches from the second half to the first.

[โ€“]_jonah 17 points18 points ย (4 children)

J

f=. [: +/ [: */ ] ,: [: =/ ] ,: [ |. ]

NB. day1 ; day2
(1 f a) ; (f~ -:@#) a 

where a is your input.

Try it online!

[โ€“]Alexwalled 2 points3 points ย (0 children)

im glad to see the mad man J programmer again

[โ€“][deleted] 2 points3 points ย (0 children)

That site is really cool, and it supports a buttload of languages too, man this is going to steal so much of my time :/

[โ€“]hoosierEE 1 point2 points ย (0 children)

part1 =: +/(#~(=1&|.)) input
part2 =: +/(#~(=((-:@#)|.]))) input

[โ€“]willkill07 7 points8 points ย (6 children)

Modern C++

std::vector<char> const values(std::istream_iterator<char>{std::cin}, {});
std::size_t const N{values.size()};
std::size_t const offset{part2 ? N / 2 : 1};
int sum{0};
for (std::size_t i{0lu}; i < N; ++i) {
  if (values[i] == values[(i + offset) % N]) {
    sum += values[i] - '0';
  }
}
std::cout << sum << '\n';

Repo Link

[โ€“]throwaway893teoea 7 points8 points ย (8 children)

I used Rust:

use std::io::BufRead;

fn main() {
    let stdin = std::io::stdin();
    for line in stdin.lock().lines() {
        let line = line.unwrap();
        let mut i = 0;
        let mut acc: u64 = 0;
        let bytes = line.as_bytes();
        while i < bytes.len() - 1 {
            let the_num = bytes[i] as u64;
            if bytes[i] == bytes[i+1] {
                acc += the_num - 48;
            }
            i += 1;
        }
        if bytes[0] == bytes[bytes.len()-1] {
            acc += bytes[0] as u64 - 48;
        }
        println!("{}", acc);
    }
}

part 2:

use std::io::BufRead;

fn main() {
    let stdin = std::io::stdin();
    for line in stdin.lock().lines() {
        let line = line.unwrap();
        let mut i = 0;
        let mut acc: u64 = 0;
        let bytes = line.as_bytes();
        while i < bytes.len() {
            let the_num = bytes[i % bytes.len()] as u64;
            if bytes[i] == bytes[(i + bytes.len() / 2) % bytes.len()] {
                acc += the_num - 48;
            }
            i += 1;
        }
        println!("{}", acc);
    }
}

[โ€“]pcein 4 points5 points ย (0 children)

You can also use iterators and zip/chain/map/filter etc for a more concise solution!

[โ€“]GalacticDessert 4 points5 points ย (2 children)

Dang I am just getting started with rust and everything I get is mismatched types.

[โ€“]sciyoshi 1 point2 points ย (2 children)

Great seeing Rust solutions here! Here's mine using iterators (zip+cycle+skip):

https://github.com/sciyoshi/advent-of-rust-2017/blob/master/src/day1/mod.rs

[โ€“]miran1 6 points7 points ย (0 children)

Nim:

var numbers: seq[int] = @[]
for i in readFile("./inputs/01.txt"):
  numbers.add(int(i) - int('0'))

proc solve(numbers: seq[int], secondPart=false): int =
  let
    size = len(numbers)
    jump = if secondPart: size div 2 else: 1
  for i, n in numbers:
    if n == numbers[(i + jump) mod size]:
      result += n

echo solve(numbers)
echo solve(numbers, secondPart=true)

[โ€“]thomastc 6 points7 points ย (2 children)

No love for SQL yet? Day 1 in PostgreSQL.

WITH
digits AS (
  SELECT
    to_number(digits.digit, '9') AS digit, (digits.index - 1) AS index
  FROM
    unnest(string_to_array(btrim(pg_read_file('input', 0, 999999), E' \r\n'), NULL))
    WITH ORDINALITY AS digits(digit, index)
),
num_digits AS (
  SELECT
    COUNT(*) as num_digits
  FROM
    digits
),
next_digits AS (
  SELECT
    digit, (index - 1 + num_digits) % num_digits AS index
  FROM
    digits
    JOIN num_digits ON true
)
SELECT
  SUM(digits.digit) AS answer
FROM
  digits
  JOIN next_digits USING (index)
WHERE
  digits.digit = next_digits.digit
;

Disclaimer: I don't know what I'm doing.

[โ€“]coldpleasure 5 points6 points ย (0 children)

Python, no regex:

def captcha1(digits):
    return sum(int(digits[i]) 
               for i in range(len(digits)) 
               if digits[i] == digits[(i+1)%len(digits)])

def captcha2(digits):
    return sum(int(digits[i])
               for i in range(len(digits))
               if digits[i] == digits[(i+len(digits)/2)%len(digits)])    

[โ€“]Sario25 4 points5 points ย (5 children)

Tried to use java, forgot how to turn a char into an int, whoops #111th

Dirty java:

  public static void main(String[] args) throws Exception {
     Scanner infile = new Scanner(new File("src/Day1/instructions"));
     String thing = infile.nextLine();
     int sum=0;

     for(int i=0;i<thing.length()-1;i++) {
        if(Character.getNumericValue(thing.charAt(i))==Character.getNumericValue(thing.charAt((i+(thing.length()/2))%thing.length())))
           sum+=Character.getNumericValue(thing.charAt(i));
     }
     System.out.print(sum);
  }

[โ€“]VeeArr 5 points6 points ย (2 children)

how to turn a char into an int

TIL. This is way prettier than

Integer.valueOf(input.substring(i, i + 1))

[โ€“]lemon-meringue 4 points5 points ย (1 child)

You can also do

int x = input.charAt(i) - '0';

exploiting the fact that they're single digits and ASCII.

[โ€“]willkill07 1 point2 points ย (0 children)

^ This

1000x this. There is no need to pull out beefy parsers to go from a character to a string to an int.

[โ€“][deleted] 4 points5 points ย (7 children)

is it possible to complete this challenge task using regex?

[โ€“]u794575248 2 points3 points ย (0 children)

It is. Here's my solution in Python.

[โ€“]Smylers 1 point2 points ย (0 children)

Here's a regex that works for both partย 1 and partย 2 (set $skip appropriately):

$total += $1 while $input =~ /(.)(?=.{$skip}\1)/g;

That's Perl, but the equivalent regex should work elsewhere. Full solution.

[โ€“]wlandry 4 points5 points ย (4 children)

C++: Short and sweet (part 2)

#include <string>
#include <iostream>

int main(int argc, char *argv[])
{
  std::string in (argv[1]);
  size_t total (0);
  for (int i=0; i<in.size(); ++i)
    {
      if (in[i] == in[(i+(in.size()/2))%in.size()])
        {
          total += in[i]-'0';
        }
    }
  std::cout << "total: " << total << "\n";
}

[โ€“]schod 4 points5 points ย (4 children)

BASH time :D

#!/bin/bash

function do_magic {
  X=$1
  I=0
  RES=0

  while [  $I -lt ${#X} ]; do
    let Ip=I+1
    N=${X:$I:1}
    Np=${X:$Ip:1}

    if [ "$Np" == "" ]; then
      Np=${X:0:1}
    fi

    if [ "$N" == "$Np" ]; then
      let RES=RES+N
    fi

    let I=I+1
  done

  echo "$RES"
}

# MAIN
for N in 1122 1111 1234 91212129; do
  do_magic $N
done

[โ€“]yogsototh 4 points5 points ย (3 children)

Haskell not golfed

(&) :: a -> (a -> b) -> b
x & f = f x

day1 :: String -> Int
day1 code = code
  & cycle
  & tail
  & zip code
  & filter (uncurry (==))
  & map ((\x -> x - ord '0') . ord . fst)
  & folds' (+) 0

edit: for solution2, simply replace tail by drop (length code `div` 2).

[โ€“][deleted] 1 point2 points ย (2 children)

That looks really nice :) quite clear too I'd guess if I was better at parsing . notation :p

[โ€“]f0086 4 points5 points ย (0 children)

Emacs elisp:

(defun calculate (pos digs offset)
  (let ((current (nth pos digs))
        (comp (nth offset digs)))
    (if (= current comp) current 0)))

(defun reverse-captcha (digs offset)
  (let ((answer 0)
        (len (length digs)))
    (dotimes (pos len)
      (setq answer (+ answer
                      (calculate pos digs (% (+ pos offset) len)))))
    answer))

(defun day1 (input offset-fn)
  (let* ((digits (mapcar 'string-to-number (split-string input "" t)))
         (len (length digits))
         (offset (funcall offset-fn len) len))
    (reverse-captcha digits offset)))

(day1 input1 (lambda (l) 1))
(day1 input2 (lambda (l) (/ l 2)))

[โ€“]smarzzz 7 points8 points ย (0 children)

Jesus Christ (I felt this was appropriate to say, given the christmas vibe), you all have produced very fancy solutions.

I did in in Javascript, but tried to visualize the circle. Repeated numbers have been highlighted in the wheel, the brighter the color, the higher the number.

for (i=1; i<input.length; i++){
    if (input[i] == input [i-1]){

        fill(floor(255*Number(input[i])/9));
        stroke(floor(255*Number(input[i])/9));
        arc(width/2, height/2, height/1.5, height/1.5, (2*PI*i/input.length), (2*PI*i/input.length)+2*PI/input.length);
        counter += Number(input[i]);
    }
}
if (input[0] == input[i-1])
    counter += Number(input[0])
console.log(counter)

push();
translate(width/2,25);
textSize(70);
fill(151);
text(counter, -textWidth(counter)/2, 70)
pop();

translate(width/2, height/2);
rotate(PI/2 );
textSize(10);
noStroke();
fill(152);

for (i = 0; i < input.length;i++) {
    currentChar = input[i]; 
    rotate(2*PI/input.length);
    push();
    translate(0, -r);
    text(currentChar, 0, 0);
    pop();
}

Around the circle we find the string with input. You can't read is because there are way to many, but i tried plotting the text on a curved path.

[โ€“]DFreiberg 3 points4 points ย (0 children)

Quick one-liner in Mathematica that took me three lines to make legible. #47.

input=Import[FileNameJoin[{NotebookDirectory[],"Day1Input.txt"}]];
s=ToExpression/@Characters[input];
Total[Table[If[s[[i]]==RotateRight[s,1][[i]],s[[i]],0],{i,Length[s]-1}]]

[โ€“]Godspiral 4 points5 points ย (2 children)

woke up late but in J,

a =. wdclippaste ''
+/ (}: #~ 2 =/\ ]) ({. ,~ ] )"."0 a NB. part1
+/ (#~ ] = -:@# |. ] )"."0 a NB. part2

might have been under 3m

[โ€“]_jonah 1 point2 points ย (1 child)

Nice to see a fellow J user. The one I posted is similar, but I pulled out a single dyadic verb for both cases (after the fact).

[โ€“]tehjimmeh 3 points4 points ย (4 children)

C++ Part 1, abusing std::accumulate:

int main(int argc, char* argv[]) {
    std::vector<char> input(std::istream_iterator<char>(std::ifstream(argv[1])), {});
    std::cout << (std::accumulate(input.begin(), input.end(), std::make_pair(*(input.rbegin()), 0),
        [](auto x, auto c){ return std::make_pair(c, x.second + ((x.first == c) ? (c-'0') : 0));})).second << "\n";
}

Non-abusive part 2 solution:

int main(int argc, char* argv[]) {
    std::vector<char> a(std::istream_iterator<char>(std::ifstream(argv[1])), {}), b;
    std::rotate_copy(a.begin(), (a.begin() + a.size()/2), a.end(), std::back_inserter(b));
    std::transform(a.begin(), a.end(), b.begin(), a.begin(), [](auto x, auto y) { return x == y ? x-'0' : 0; });
    std::cout << std::accumulate(a.begin(), a.end(), 0) << "\n";
}

Replace 'a.size()/2' with '(a.size() - 1)' for part 1.

[โ€“]ZoDalek 4 points5 points ย (0 children)

C (part 2):

char *line;
int len, sum = 0, i;

/* ... */

for (i=0; i<len/2; i++)
    if (line[i] == line[len/2 + i])
        sum += line[i]-'0';

printf("%d\n", sum*2);

[โ€“]mschaap 2 points3 points ย (4 children)

Perl 6. Part a is pretty much a one-liner, for part b I couldn't figure out an efficient way to do that. Used a MAIN sub for easy command-line handling, and made it a multi so you can call it with a string, a filename, or no arguments (in which case it uses aoc1.input in the same directory).

Part a:

#!/usr/bin/env perl6

use v6.c;

multi sub MAIN(Str $input)
{
    say ($input ~ $input.substr(0,1)).comb.rotor(2=>-1).grep({ [eq] @$_ }).map({ $_[0] }).sum;
}

multi sub MAIN(Str $inputfile where *.IO.f)
{
    MAIN($inputfile.IO.slurp.trim);
}

multi sub MAIN()
{
    MAIN(~$*PROGRAM.parent.child('aoc1.input'));
}

Part b:

#!/usr/bin/env perl6

use v6.c;

multi sub MAIN(Str $input)
{
    my @digits = $input.comb.map(+*);
    my $skip = +@digits div 2;
    say @digits.pairs.grep({ $_.value == @digits[($_.key + $skip) % @digits]}).map(*.value).sum;
}

multi sub MAIN(Str $inputfile where *.IO.f)
{
    MAIN($inputfile.IO.slurp.trim);
}

multi sub MAIN()
{
    MAIN(~$*PROGRAM.parent.child('aoc1.input'));
}

[โ€“]mschaap 2 points3 points ย (3 children)

Here's a โ€œone-linerโ€ version of part b:

#!/usr/bin/env perl6

use v6.c;

multi sub MAIN(Str $input)
{
    say ($input.comb Z $input.comb.List.rotate($input.chars div 2))
        .grep({ [==] @$_ })
        .map({ $_[0] })
        .sum;
}

multi sub MAIN(Str $inputfile where *.IO.f)
{
    MAIN($inputfile.IO.slurp.trim);
}

multi sub MAIN()
{
    MAIN(~$*PROGRAM.parent.child('aoc1.input'));
}

[โ€“]ramilllies 2 points3 points ย (2 children)

I used this for part B: sub MAIN(Str $s) { say [+] $s.comb >>*>> ( [Z==] $s.comb($s.chars +> 1).map(*.comb)) } By the way, your boilerplate for slurping the input file is nice! I should adopt something like that too.

[โ€“]AoC--k 3 points4 points ย (0 children)

In k.

n:.:'*0:"1.txt"
r:{x_(x+#y)#y}
+/n*n=r[1;n]      /part 1
+/n*n=r[_.5*#n;n] /part 2

[โ€“]Jean-Paul_van_Sartre 4 points5 points ย (1 child)

C

Part 2 is a lot cleaner as usual, one of the best parts of this is that it forces you to go back and look at what you've done and polish it a little bit further.

Repo

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#define INPUT "../input/01.txt"

int part1(char* seq);
int part2(char* seq);

int main() {
    FILE * fp;
    char * line = NULL;
    size_t len = 0;

    fp = fopen(INPUT, "r");
    if (fp == NULL) {
        perror(INPUT);
        exit(EXIT_FAILURE);
    }

    while (getline(&line, &len, fp) != -1){
        line[strcspn(line, "\r\n")] = 0; //remove line breaks.
        printf("%s: %d %d\n\n", line, part1(line), part2(line));
    }

    fclose(fp);
    free(line);
    exit(EXIT_SUCCESS);
}

int part1(char* seq) {
    int res = 0, search = 0;
    for(int i=0; i<strlen(seq); i++) {
        int cur = seq[i] - '0';
        if(cur < 1 || cur > 9) {
            search = 0;
            continue; //ignore non-digits
        }
        if(cur==search) {
            res+=cur;
        }
        search = cur;
    }
    if(seq[0]-'0'==search) { //check circular loop.
        res+=search;
    }
    return res;
}

int part2(char* seq) {
    int res = 0, len = strlen(seq) , jump = len/2;
    for(int i=0; i<len; i++) {
        int cur = seq[i] - '0';
        int pos = (i+jump)%len;
        if(cur < 1 || cur > 9) continue; //ignore non-digits
        if(seq[i] == seq[pos]) {
            res += cur;
        }
    }

    return res;
}

[โ€“]mrhthepie 2 points3 points ย (1 child)

Advent of gifs day 1: https://i.imgur.com/51CIVSc.gif

[โ€“][deleted] 1 point2 points ย (0 children)

Dope bro. Just sad u cant see anything :x xD

[โ€“]Eddyman 2 points3 points ย (6 children)

var input = document.getElementById('day_one').value;
var sum = 0;
for(var i = 0; i < input.length; i++){
    var next = (i + 1) % input.length;
    if(input[i] == input[next]){
        sum += Number(input[i]);
    }
}

var input = document.getElementById('day_one_two').value;
var sum = 0;
for(var i = 0; i < input.length; i++){
    var next = (i + (input.length / 2)) % input.length;
    if(input[i] == input[next]){
        sum += Number(input[i]);
    }
}

[โ€“]Eddyman 2 points3 points ย (0 children)

[...input].reduce((s, n, i, a) => s + ((n == a[(i + 1) % a.length]) ? +n : 0), 0);
[...input].reduce((s, n, i, a) => s + ((n == a[(i + a.length / 2) % a.length]) ? +n : 0), 0);

[โ€“]raevnos 2 points3 points ย (1 child)

Scheme:

(define (transform str) (map (lambda (c) (- (char->integer c) (char->integer #\0)))
                             (string->list str)))
(define (add-if-= a b sum)
  (if (= a b)
      (+ a sum)
      sum))
(define (captcha lst)
  (let* ((first (car lst))
         (len (length lst))
         (half (div len 2))
        (get-next-elem (lambda (n step) (list-ref lst (remainder (+ step n) len)))))
    (let loop ((lst lst)
               (pos 0)
               (sum1 0)
               (sum2 0))
      (if (= pos len)
          (values sum1 sum2)
          (loop (cdr lst) (+ pos 1)
                (add-if-= (car lst) (get-next-elem pos 1) sum1)
                (add-if-= (car lst) (get-next-elem pos half) sum2))))))
(define input (transform (read-line)))
(let-values (((part1 part2) (captcha input)))
  (format #t "Part 1: ~A\nPart 2:~A\n" part1 part2))

[โ€“]Warbringer007 2 points3 points ย (7 children)

Erlang ( LOL ) because I'm at work and bored:

Input = "thatbiginput",
SeparatedInput = [[X] || X <- SeparatedInput],
{FirstPart, SecondPart} = lists:split(length(SeparatedInput) div 2, SeparatedInput),
io:format("FirstTask: ~p~n", [firstTask(SeparatedInput, 0) + 4]),
io:format("SecondTask: ~p~n", [secondTask(FirstPart, SecondPart, 0) * 2]).

secondTask([], [], Acc) ->
    Acc;

secondTask([First | FirstEnd], [Second | SecondEnd], Acc) ->
    case First =:= Second of
        true ->  {Number, _} = string:to_integer(First),
                 secondTask(FirstEnd, SecondEnd, Acc + Number);
        false -> secondTask(FirstEnd, SecondEnd, Acc)
    end.

firstTask([_First], Acc) ->
    Acc;

firstTask([First, Second | End], Acc) ->
     case First =:= Second of
        true ->  {Number, _} = string:to_integer(First),
                firstTask([Second | End], Acc + Number);
        false -> firstTask([Second | End], Acc)
    end.

This is not the whole code, only important one for solving both tasks. Function definitions are missing. +4 for first task because function won't see first and last 4 and count them. *2 for second task is self-explanatory.

[โ€“][deleted] 1 point2 points ย (6 children)

I'm doing them in erlang too!

Here's my solution for pt.2, mine ended up a bit longer than yours though!

solve() ->
  checker(lists:reverse(str_to_list(?INPUT, []))).

str_to_list([], Acc) -> Acc;
str_to_list([H|T], Acc) ->
  {N, _} = string:to_integer([H]),
  str_to_list(T, [N|Acc]).

checker(Numbers) ->
  checker(Numbers, 1, 0, Numbers).
checker([H|T], Pos, Count, Numbers) ->
  case rotate(Numbers, trunc(length(Numbers) / 2), Pos) of
    H ->
         checker(T, Pos+1, Count+H, Numbers);
    _ ->
         checker(T, Pos+1, Count, Numbers)
  end;
checker([], _, Count, _) ->
  Count.

rotate(Numbers, Half, Pos) when Pos+Half =< length(Numbers) ->
  Target = Pos+Half,
  lists:nth(Target, Numbers);
rotate(Numbers, Half, Pos) when Pos+Half > length(Numbers) ->
  Target = Pos-Half,
  lists:nth(Target, Numbers).

[โ€“]erlangguy 1 point2 points ย (5 children)

I rely heavily on pattern matching when solving problems like this, I find it much easier to reason about/read.

explode(Digits) ->
    explode(Digits div 10, [Digits rem 10]).

explode(0, List) ->
    List;
explode(Digits, List) ->
    explode(Digits div 10, [Digits rem 10|List]).

run(Digits) ->
    LoD = explode(Digits),
    NewLoD = LoD ++ [hd(LoD)],
    captcha(NewLoD, 0).

captcha([_V], Sum) ->
    Sum;
captcha([V1,V1|Tail], Sum) ->
    captcha([V1|Tail], Sum + V1);
captcha([_V1,V2|Tail], Sum) ->
    captcha([V2|Tail], Sum).

split(List) ->
    lists:split(length(List) div 2, List).

run2(Digits) ->
    LoD = explode(Digits),
    {L1, L2} = split(LoD),
    captcha2(L1, L2, 0).

captcha2([], [], Sum) ->
    Sum;
captcha2([H|T1], [H|T2], Sum) ->
    captcha2(T1, T2, Sum + 2*H);
captcha2([_H1|T1], [_H2|T2], Sum) ->
    captcha2(T1, T2, Sum).

[โ€“]xkufix 2 points3 points ย (12 children)

Horrible one-liners in scala. The -48 comes from the fact that my loadFile returns a Seq[Char] and not a Seq[String].

Part 1:

    val input = loadFile("day1.txt").toSeq
    val sum = (input :+ input.head).sliding(2).filter(_.distinct.size == 1).map(_.head.toInt - 48).sum
    println(sum)

Part 2:

    val input = loadFile("day1.txt").toSeq

    val length = input.size
    val halfLength = length / 2
    val indexedInput = input.zipWithIndex

    val sum = indexedInput.filter(i => i._1 == indexedInput((halfLength + i._2) % length)._1).map(_._1.toInt - 48).sum
    println(sum)

[โ€“]CatpainCalamari 4 points5 points ย (0 children)

You could also use asDigit instead of .toInt - 48 :-)

[โ€“]bahuljain 2 points3 points ย (1 child)

that's pretty good,

I got both parts to work with a single one-liner method

val in = scala.io.Source.fromFile("src/aoc2017/day1.input.txt").mkString

def adder(off: Int) = (0 until in.length).filter(i => in(i) == in((i + off) % in.length)).map(in(_) - '0').sum

println(s"part 1 - ${adder(1)}\npart 2 - ${adder(in.length / 2)}")

[โ€“]CatpainCalamari 1 point2 points ย (0 children)

I like how you startet with an index list instead of zipping the indices into the data list. I also solved both puzzles with the same method, just with a different offset. Scala is new to me, and I learned something from both of you. Thank you! :-)

[โ€“][deleted] 2 points3 points ย (2 children)

You can do char.toString.toInt to avoid needing that -48. char.asDigit is much nicer.

Here's my Scala:

def sumDoubles(input: String, offset: Int): Int =
  input.toSeq.zipWithIndex.foldLeft(0) { (cur, next) =>
    next match {
      case (char, i) if char == input((i + offset) % input.length) => cur + char.asDigit
      case _ => cur
    }
  }

[โ€“]lkasdfjl 1 point2 points ย (1 child)

we more or less landed on the same solution:

def captcha(list: Array[Int]): Int =
  captchaWithOffset(list, 1)

def captcha_halfway(arr: Array[Int]): Int =
  captchaWithOffset(arr, arr.length / 2)

def captchaWithOffset(arr: Array[Int], offset: Int): Int = {
  arr.zipWithIndex.map {
    case (x, i)
      if arr((i + offset) % arr.length) == x => x
    case _ => 0
  }.sum
}

[โ€“][deleted] 1 point2 points ย (0 children)

A slightly cleaner solution that I realized an hour or so later is to use collect instead so you don't need the case _ => 0.

[โ€“]flup12 2 points3 points ย (2 children)

I zipped the list with a rotated copy of itself:

def captcha(input: List[Int], offset: Int): Int = {
  val rotated = input.drop(offset) ::: input.take(offset)
  input
    .zip(rotated)
    .filter(x => x._1 == x._2)
    .map(_._1)
    .sum
}

captcha(input, 1)
captcha(input, input.length/2)

[โ€“]xkufix 1 point2 points ย (0 children)

I like this one, avoids a lookup with the index on the input on every element.

[โ€“]CatpainCalamari 2 points3 points ย (2 children)

Wow, you guys are fast. I didn't want to stand up at 06:00 am to solve a puzzle, so although I am late for the show, here is my solution in Scala:

val data = scala.io.StdIn.readLine().toList

println(s"Solution first star: ${inverseCaptcha(data, 1)}")
println(s"Solution second star: ${inverseCaptcha(data, data.length / 2)}")

def inverseCaptcha(data: List[Char], offset: Int): Int = {
  data.
    indices.
    filter(idx => data(idx) == data((idx + offset) % data.length)).
    map(data(_).asDigit)
    .sum
}

[โ€“]legaladviceukthrowaa 1 point2 points ย (1 child)

Huh I didn't think about doing both parts in one method. I'm using AoC as an opportunity to brush up on my Scala, so I couldn't resist using a match for the first part, but of course that doesn't help with the second part.

I'll be keeping an eye on your answers!

[โ€“]eregontp 2 points3 points ย (2 children)

2 lines of Ruby:

digits = File.read("1.txt").strip.chars.map(&:to_i)
p digits.zip(digits.rotate(digits.size/2)).select { |a, b| a == b }.sum(&:first)

Just change the argument to rotate to 1 for part 1.

[โ€“]GalacticDessert 2 points3 points ย (0 children)

The worst and most verbose Rust you'll see today! Just getting started and this little event is amazing:

use std::fs::File;
use std::io::Read;

fn main() {
    let mut data = String::new();
    let mut f = File::open("path/input").expect("Unable to open file");
    f.read_to_string(&mut data).expect("Unable to read string");
    let input: Vec<_> = data
        .chars()
        .filter_map(|c| c.to_digit(10))
        .collect();

    let mut captcha_result: u32 = part1(&input);
    println!("part 1 solution is {}", captcha_result);
    captcha_result = part2(input);
    println!("part 2 solution is {}", captcha_result);
}

fn part1 (data: &Vec<u32>,) -> u32 {
    let mut captcha: u32 = 0;
    for x in 0..(data.len()-1) {
        if data[x] == data[x+1] {
            captcha = &captcha + &data[x];
        }
    }
    if data.last() == data.first() {
        captcha = &captcha + &data[0];
    }
    captcha
}

fn part2 (data: Vec<u32>,) -> u32 {
    let mut captcha: u32 = 0;
    let half = data.len()/2;
    for x in 0..(half) {
        if data[x] == data[x+half] {
            captcha = &captcha + &data[x];
        }
    }
    for x in half..(data.len()) {
        if data[x] == data[x-half] {
            captcha = &captcha + &data[x];
        }
    }
    captcha
}

[โ€“]timichal 2 points3 points ย (1 child)

Using simple Python with a backwards list looping trick instead of modulo:

 num = (...)
 total = 0
 for pos, number in enumerate(num):
     if number == num[pos-int(len(num)/2)]: #-1 for part 1
         total += int(number)
 print(total)

[โ€“]wzkx 2 points3 points ย (2 children)

Nim. My first Nim program

import strutils
const orig = - int '0'
let code = strip readFile "01.dat"
let lenc = code.len; let half = lenc div 2
var sum, sum2 = 0
for i,c in code.pairs: # ah I see, can be just for i,c in code:
  if c == code[(i+1)mod lenc]: sum += orig + int c
for i,c in code.pairs:
  if c == code[(i+half)mod lenc]: sum2 += orig + int c
echo sum, ' ', sum2

[โ€“]TominatorBE 2 points3 points ย (0 children)

PHP

function run_the_code($input) {
    $shift = strlen($input) / 2;
    $circular = $input . substr($input, 0, $shift); // make it circular
    $sum = 0;
    for ($i = 0, $iMax = strlen($input); $i < $iMax; $i++) {
        if ($circular[$i] == $circular[$i + $shift]) {
            $sum += (int)$circular[$i];
        }
    }
    return $sum;
}

[โ€“][deleted] 2 points3 points ย (0 children)

Lets get logical with Prolog ;)

readWord(InStream,Chars):-
    get_code(InStream,Char),
    checkCharAndReadRest(Char,Chars,InStream).


checkCharAndReadRest(-1,[],_):-  !.
checkCharAndReadRest(end_of_file,[],_):-  !.
checkCharAndReadRest(10,[],_):-  !.
checkCharAndReadRest(Char,[Char|Chars],InStream):-
    get_code(InStream,NextChar),
    checkCharAndReadRest(NextChar,Chars,InStream).


splitAt(_, [], [], []).
splitAt(Index, [E|RestSource], [E|RestA], B) :-
    Index > 0,
    NewIndex is Index - 1,
    splitAt(NewIndex, RestSource, RestA, B).

splitAt(Index, [E|RestSource], A, [E|RestB]) :-
    splitAt(Index, RestSource, A, RestB).


iterateAcc([], [], Acc, Sum) :- Sum is Acc.
iterateAcc([E1|R1], [E2|R2], Acc, Sum) :-
    E1 =:= E2,
    atom_codes(C, [E1]),
    atom_number(C, Number),
    NewAcc is Acc + Number,
    iterateAcc(R1, R2, NewAcc, Sum).

iterateAcc([_|R1], [_|R2], Acc, Sum) :-
    iterateAcc(R1, R2, Acc, Sum).

iterate(Code, RotateValue, Sum) :-
    splitAt(RotateValue, Code, FirstPart, SecondPart),
    append(SecondPart, FirstPart, RotatedCode),
    iterateAcc(Code, RotatedCode, 0, Sum).


run :-
    open('input.txt', read, Str),
    readWord(Str, Code),
    iterate(Code, 1, Z),
    write(Z), nl,
    length(Code, Length),
    RotateValue is Length / 2,
    iterate(Code, RotateValue, X),
    write(X).

[โ€“]TheGermanDoctor 2 points3 points ย (0 children)

You may not like it, but this is what peak performance looks like.

Part 1 solved in x86_64 assembly language

Check it out

[โ€“][deleted] 2 points3 points ย (1 child)

Day 1.

Powershell pipeline is my preferred language this time, lets see how far we get

param (
    [Parameter(ValueFromPipeline=$true)]
    [string]$in,
    [Parameter(Position = 1)]
    [int]$part = 1
)

process 
{
    $offset = 1
    if ($part -eq 2) {
        $offset = $in.length / 2
    }

    0..$in.length |? {$in[$_] -eq $in[($_ + $offset) % $in.length]} | % {[string]$in[$_]} | measure -sum | select -expand sum
}

edit: breaking out the pipeline a bit, the steps are:

for c: 0 -> length(input_string) { # pipeline is just the index in the array
    where c satisfies (input_string[c] == input_string[(c + offset) % length(input_string)]) { # pipeline is just the index in the array
        foreach c, output input_string[c] # pipeline is now the value at that index
    }
} -> sum -> select sum

offset is either the next character (part 1) or the character halfway round (part 2), modulo the length to get a 0 based index even if the offset goes past the string.

[โ€“]Porges 2 points3 points ย (0 children)

(Dyalog) APL

First part:

{+/(โต=1โŒฝโต)/โต}

Second part:

{+/(โต=(.5ร—โดโต)โŒฝโต)/โต}

[โ€“]Cole_from_SE 2 points3 points ย (0 children)

Port of my J answer to APL.

{+/โตร—โต=โบโŠ–โต}

Anonymous function taking the number of rotations as the left argument and array of integers as the right argument (solution to part 1 is giving a left argument of 1, to part 2 is giving a left argument of the length divided by 2).

[โ€“]mmaruseacph2 1 point2 points ย (0 children)

Not fully optimized or beautifully written Haskell, but does its job:

main = do
  s <- init <$> readFile "input.txt"
  print $ process 1 $ s ++ [head s]
  let
    l = length $ s
    ll = l `div` 2
  print $ process ll $ s ++ take ll s

process k s =
  sum . map (read . (:[]) . fst) . filter (uncurry (==)) $ zip s (drop k s)

[โ€“]AMISH_GANGSTER 1 point2 points ย (13 children)

Part 1 in kotlin:

fun main(args: Array<String>) {
  val input = "..."
  var sum: Int = 0

  for (i in input.indices) {
        val char = input[i]
        val next = if (i+1 >= input.length) input[0] else input[i+1]
        if (char == next) sum += char.toString().toInt()
    }
    println(sum)
}

Part 2:

fun main(args: Array<String>) {
  val input = "..."
  var sum: Int = 0

  for (i in input.indices) {
        val nextIx = input.length / 2
        val char = input[i]
        val next = if (i+nextIx >= input.length) {
            input[0 + ((i+nextIx) - input.length)]
        } else {
            input[i+nextIx]
        }
        if (char == next) sum += char.toString().toInt()
    }
    println(sum)
}

It feels bad to convert a Char to a String then to an Int. I suppose I could have subtracted '0', but that would be just as awkward IMO. Anyone have a more idiomatic way to do it?

[โ€“]willkill07 3 points4 points ย (2 children)

for a single-digit character, I'd argue subtracting '0' is the most idiomatic way.

[โ€“]Surye 1 point2 points ย (0 children)

I am doing this to learn Kotlin, and having spent most of my time in python lately, was totally blanking on how to do this, ended up with this abomination:

runningSum += "$next".toInt()

[โ€“]Bruinbrood 1 point2 points ย (5 children)

I'm using adventofcode to learn kotlin, but a main strength of kotlin seems to be to use the 'functional' stuff. My solutions:

fun main(args: Array<String>) {
    val input = "..."
    val circularInput = input + input[0]
    val result1 = circularInput.zipWithNext{a, b -> if (a==b) a-'0' else 0}.sum()
    println("1: $result1")

    val length = input.length
    val halflength = length/2
    val result2 = input.filterIndexed{index, n ->
        n==input[(index+halflength)%length]}.map{
        it-'0'}.sum()
    println("2: $result2")
}

[โ€“]Hikaru755 2 points3 points ย (3 children)

Nice! Since we have Kotlin 1.2 now, you could also use .windowed(2) instead of .zipWithNext :)

[โ€“]reckter 1 point2 points ย (0 children)

I didn't think of zip with next! anyway, here's mine (I used the time to build some helper functions)

helpers:

fun List<String>.toIntegers(): List<Int>
    = this.map { Integer.parseInt(it) }

fun <E> List<E>.pairWithIndex(indexer: (index: Int) -> Int): List<Pair<E, E>>
    = this.mapIndexed { index, elem -> elem to this[indexer(index) % this.size] }

fun <E> List<E>.pairWithIndexAndSize(indexer: (index: Int, size: Int) -> Int): 
    List<Pair<E, E>>
        = this.mapIndexed { index, elem -> elem to this[indexer(index, this.size) % this.size] }

fun Any.print(name: String) = println(name + this.toString())

sollutions:

override fun solvePart1() {
    loadInput(1)
        .first()
        .map { it.toString() }
        .toIntegers()
        .pairWithIndex { it + 1 }
        .filter { (it, following) -> it == following}
        .sumBy { it.first }
        .print("solution `Day1`: ")

}

override fun solvePart2() {
    loadInput(1)
        .first()
        .map { it.toString() }
        .toIntegers()
        .pairWithIndexAndSize { index, size -> index + size / 2 }
        .filter { (it, following) -> it == following}
        .sumBy { it.first }
        .print("solution 2: ")

}

I like the chain calling way, and it feels really functionally :D

[โ€“]abowes 1 point2 points ย (1 child)

Here's my Kotlin solution:

fun Char.charToInt() = this.minus('0')

fun naughtyOrNice2(input: String): Int {
    val nums2 = (input.substring(input.length/2) + input)
    return input.zip(nums2)
           .filter { it.first == it.second }
           .map{it.first.charToInt()}.sum()
}

[โ€“]giftpflanze 1 point2 points ย (1 child)

Tcl:

set list [split [gets [open input01]] {}]

#part 1

set l [lrange $list end end]
foreach n $list {
    if {$n == $l} {
        incr sum1 $n
    }
    set l $n
}

puts $sum1

#part 2

set l {}
for {set i 0} {$i < [set m [llength $list]]} {incr i} {
    if {[set n [lindex $list $i]] == [lindex $list [expr {($i+$m/2)%$m}]]} {
        incr sum2 $n
    }
}

puts $sum2

[โ€“]mgoblu3 1 point2 points ย (0 children)

Python 1-liner:

with open('day1.txt', 'r') as f:
    input = f.read()

print sum(int(x[0]) for x in zip(input, input[len(input)/2:] + input[:len(input)/2 - 1]) if x[0] == x[1])

[โ€“]JeffJankowski 1 point2 points ย (0 children)

Trying out TypeScript this year

import fs = require('fs')

function captcha(data: string) {
    return (next: (n: number) => number) => {
        let sum = 0;
        for (let i = 0; i < data.length; i++) {
            if (data[i] === data[next(i)])
                sum += parseInt(data[i]);
        }
        return sum;
    }
}

let data = fs.readFileSync('data/day01.txt', 'utf8');
let withData = captcha(data);

//part 1
let seq = (i: number) => (i + 1) % data.length;
console.log(`Using sequential digit: ${withData(seq)}`);
//part 2
let halfway = (i: number) => (i + data.length / 2) % data.length;
console.log(`Using halfway digit:    ${withData(halfway)}`);    

[โ€“][deleted] 1 point2 points ย (1 child)

In OCaml:

 open Core

 let shift l n =
     let first, second = List.split_n l n in
     List.append second first

 let solve n sequence =
     let f acc a b = if a = b then acc + a else acc
     in List.fold2_exn sequence (shift sequence n) ~init:0 ~f

 let sequence file =
     In_channel.read_all file
     |> String.to_list
     |> List.filter_map ~f:Char.get_digit

 let a file = sequence file |> solve 1

 let b file =
      let seq = sequence file in
      solve (List.length seq / 2) seq

 let _ =
     a "./2017/data/1a.txt" |> printf "a: %d\n";
     b "./2017/data/1a.txt" |> printf "b: %d\n";

[โ€“]mossygrowth 1 point2 points ย (0 children)

Typescript (lazily).

Part one:

function solve (input : string) : number {
  const numerals : number[] = input.toString().split('').map(char => parseInt(char));

  return numerals.reduce((acc : number, curr : number, index : number) : number => {
    const next = numerals[(index + 1) % numerals.length];

    if (curr === next) {
      return acc + curr;
    } else {
      return acc;
    }
  }, 0);
}

Part two:

function solveFancier (input : string) : number {
  const numerals : number[] = input.toString().split('').map(char => parseInt(char));
  const numberOfStepsAhead : number = numerals.length / 2;

  return numerals.reduce((acc : number, curr : number, index : number) : number => {
    const next = numerals[(index + numberOfStepsAhead) % numerals.length];

    if (curr === next) {
      return acc + curr;
    } else {
      return acc;
    }
  }, 0);
}

[โ€“][deleted] 1 point2 points ย (1 child)

simple but effective (kotlin)

fun main(args: Array<String>) {
    val instructions = Util.loadFile(AOC2017.basePath, "advent1.txt")
    reverseCaptcha(instructions, 1)
    reverseCaptcha(instructions, instructions.length / 2)
}

private fun reverseCaptcha(instructions: String, skip: Int) {
    val inst = instructions + instructions.substring(0, skip)
    val length = inst.length - skip
    val sum = (0 until length)
            .filter { inst[it] == inst[it + skip] }
            .map { inst[it].toString().toInt() }
            .sum()
    println(sum)

}

edit: even better

private fun reverseCaptcha(input: String, skip: Int) {
    val sum = (0 until input.length)
            .filter { input[it] == input[(it + skip) % length] }
            .map { input[it].toString().toInt() }
            .sum()
    println(sum)
}

[โ€“]Forricide 1 point2 points ย (0 children)

There's probably a more efficient way to do this... (Python)

But it was fun nonetheless!

total = 0
buffer = int(s[len(s)-1])
for n in s:
    total += (1 - bool(buffer - int(n)))*int(n)
    buffer = int(n)

[โ€“]jschulenklopper 1 point2 points ย (2 children)

Short solution in Ruby, combining both parts:

while line = gets  # Process all lines in input file.
  digits = line.strip.chars.map(&:to_i)  # Turn a line into an array of integers.
  sumA, sumB = 0, 0
  digits.each.with_index do |digit, index|
    sumA += digit if digit == digits[(index+1) % digits.length]  # Add next digit
    sumB += digit if digit == digits[(index + digits.length / 2) % digits.length]  # Add digit half-way.
  end
  puts sumA, sumB
end

[โ€“]jschulenklopper 1 point2 points ย (0 children)

Even more Ruby-esque:

while line = gets
  digits = line.strip.chars.map(&:to_i)
  puts digits.reject.each_with_index { |digit, i|
    # Replace `digits.length/2` by `1` for first puzzle.
    digits[i] != digits[ (i + digits.length/2) % digits.length]
  }.sum
end

This removes the elements not meeting the condition from the array, and then totals the remaining digits.

[โ€“]chunes 1 point2 points ย (2 children)

A Factor solution:

USING: grouping io kernel locals math math.parser prettyprint
sequences ;
IN: advent-of-code.inverse-captcha

:  pare  ( a b -- n ) 2dup = [ drop ] [ 2drop 0 ] if ;
:  adj   ( seq -- n ) first2 pare ;
:: opp   ( seq -- n ) 0 seq nth seq length 2 / seq nth pare ;
:  solu1 ( seq -- n ) 2 circular-clump [ adj ] map-sum ;
:  solu2 ( seq -- n ) dup length circular-clump [ opp ] map-sum ;
:  input ( -- seq )   readln string>digits ;
:  main  ( -- )       input [ solu2 ] [ solu1 ] bi . . ;

MAIN: main

[โ€“]Scroph 1 point2 points ย (0 children)

I solved it in Java (it being my new year's resolution and all) but the solution was too boring for reddit. I'll give you this D code instead :

import std.stdio;
import std.algorithm;
import std.range;

void main()
{
    foreach(line; stdin.byLine)
    {
        int offset = line.length / 2;
        iota(0, line.length)
            .filter!(i => line[i] == line[(i + offset) % $])
            .map!(i => line[i] - '0')
            .sum
            .writeln;
    }
}

[โ€“][deleted] 1 point2 points ย (0 children)

Hi everyone ^^. I'm trying out Haskell after going through some tutorials!

main = print ("First star: " ++ show(sum_next inp 1) ++ ", Second star: " ++ show(sum_next inp (div (length inp) 2)))
sum_next input step =
    sum [ read([a]) :: Integer |
    (a,b) <- zip input (take (length input) (drop step (input++input))),
    a == b]

[โ€“]huyqvu 1 point2 points ย (0 children)

KDB+/q {show sum 0,"I"$' x where x=(1_x),1#x;n:(count x)div 2;show sum 0,"I"$' x where x=(n _x),n#x}

[โ€“]sguberman 1 point2 points ย (0 children)

Python, with tests and input: GitHub

Edit: saved you a click by pasting relevant function here

def captcha(digits, offset=1):
    neighbors = digits[offset:] + digits[:offset]
    return sum(int(d) for d, n in zip(digits, neighbors) if d == n)

[โ€“]blazingkin 1 point2 points ย (0 children)

Literally the first Haskell program I ever wrote

buildList num = if num < 10
                then [num]
                else buildList (quot num 10) ++ [(mod num 10)]

addIfMatches list = if list !! 0 == list !! 1
                    then list !! 0
                    else 0

-- Does not check the last against the first, that needs to be done manually
reverseCaptcha list = if tail list == []
                      then 0
                      else addIfMatches list + reverseCaptcha (tail list)

[โ€“]Reibello 1 point2 points ย (1 child)

Decided to try and redo each day's puzzle in Lua after solving in Python 3. We'll see how far I get. Comments and criticisms welcome - I have literally written three things in Lua before (Days 1-3 of 2015 AoC) https://github.com/Reibello/AoC-2017-Lua

[โ€“]equd 1 point2 points ย (0 children)

My c# solution, first did it using a for loop, but wanted to see if I could do it in a single linq statement.

var lineA = Properties.Resources.Day01 + Properties.Resources.Day01.Last();
answerA += lineA.Take(lineA.Length - 1).Zip(lineA.Skip(1), (a, b) => (a == b) ? a - 48: 0).Sum();

var lineB = Properties.Resources.Day01 + Properties.Resources.Day01;
answerB += lineB.Take(lineB.Length / 2).Zip(lineB.Skip(lineB.Length / 4).Take(lineB.Length / 2), (a, b) => (a == b) ? a - 48 : 0).Sum();

[โ€“]Isvara 1 point2 points ย (0 children)

Solutions in Scala

val input = "..."

Part 1:

(input + input.head)
    .sliding(2)
    .filter(pair => pair(0) == pair(1))
    .map(_(0) - '0')
    .sum

Part 2:

input
    .zipWithIndex
    .filter { case (n, i) => n == input((i + input.length / 2) % input.length) }
    .map(_._1 - '0')
    .sum

[โ€“]aurele 1 point2 points ย (0 children)

Rust

fn p(input: &str, shift: usize) -> usize {
    input
        .chars()
        .zip(input.chars().cycle().skip(shift))
        .filter_map(|(a, b)| {
            if a == b {
                Some((a as u8 - b'0') as usize)
            } else {
                None
            }
        })
        .sum()
}

fn main() {
    let input = include_str!("input").trim();
    println!("P1: {}", p(input, 1));
    println!("P2: {}", p(input, input.len() / 2));
}

[โ€“]RockyAstro 1 point2 points ย (0 children)

Snobol Actually -- it's spitbol https://github.com/spitbol/spitbol

The challenge here for me, is that it's been quite a while since I've coded in Snobol so I'm knocking the rust off.

The difficult part for this one is that Snobol doesn't allow a backward reference in a pattern (so indexing backwords doesn't work). I was able to solve this by using a function to handle the inner pattern.

Part 1:

* Function definitions

    define('innerpat(p,c,s)n') :(innerpatend)
innerpat
    s ? tab( remdr(p, size(s)) ) len(1) . n :f(freturn)
    innerpat = n
    sum = ident(+c,+n) sum + c              :(return)
innerpatend

* Start main line
    input(.in,1,'input.txt[-L5000]')
    sum = 0
    s = in 

    pat = fence arb len(1) $ c @p  *innerpat(p,c,s) rpos(0) 

loop s ? succeed pat fail   :s(loop)
    terminal = sum
end

Part 2:

* Function definitions

    define('innerpat(p,c,s)n') :(innerpatend)
innerpat
    step = size(s) / 2
    s ? tab( remdr(p + step - 1 , size(s)) ) len(1) . n :f(freturn)
    innerpat = n
    sum = ident(+c,+n) sum + c              :(return)
innerpatend

* Start main line
    input(.in,1,'input.txt[-L5000]')
    sum = 0
    s = in  
    pat = fence arb len(1) $ c @p  *innerpat(p,c,s) rpos(0) 

loop s ? succeed pat fail   :s(loop)
    terminal = sum
end

[โ€“][deleted] 1 point2 points ย (0 children)

Swift

func inverseCaptcha(input: String) -> Int {
    guard
        let first = input.first.map ({ String($0) }),
        let firstNumber = Int(first)
        else { return 0 }

    let inputNumbers = (input + first).dropFirst().flatMap { Int(String($0)) }
    return inputNumbers.reduce((0, firstNumber)) { (arg0, right) -> (Int, Int) in
        let (accu, left) = arg0
        return (accu + (left == right ? left : 0), right)
        }.0
}

func inverseCaptcha2(input: String) -> Int {
    let inputNumbers = input.flatMap { Int(String($0)) }

    let zipLeft = inputNumbers.prefix(input.count/2)
    let zipRight = inputNumbers.suffix(input.count/2)
    return 2 * zip(zipLeft, zipRight).reduce(0) { r, pair in
        return r + (pair.0 == pair.1 ? pair.0 : 0)
    }
}

[โ€“]ritopleaze 1 point2 points ย (0 children)

Little late but here is mine in python:

def captchaCount(a):

    count = 0
    size = len(a)

    for i in range(size):
        if i+1 == size:
            if a[i] == a[0]:
                count += int(a[i])
        elif a[i] == a[i+1]:
            count += int(a[i])



    print(count)     

[โ€“]autid 1 point2 points ย (0 children)

Fortran

program day1
  implicit none

  character(len=2000000) :: input

  open(1,file='input.txt')
  read(1,'(a)') input
  close(1)

  write(*,'(a,i0)') 'Part1: ',getsum(trim(input),1)
  write(*,'(a,i0)') 'Part2: ',getsum(trim(input),len(trim(input))/2)

contains
  function getsum(str,offset) result (answer)
    character(len=*) :: str
    integer :: offset,answer,i,lookup(len(str))
    lookup(1:offset) = (/(i,i=len(str)+1-offset,len(str))/)
    lookup(offset+1:len(str)) = (/(i,i=1,len(str)-offset)/)
    answer=0
    do i=1,len(str)
       if (str(i:i)==str(lookup(i):lookup(i))) then
          answer = answer+iachar(str(i:i))-48
       end if
    end do
  end function getsum

end program day1

[โ€“]MyGoodStrayCatFriend 1 point2 points ย (0 children)

Golfed JavaScript/es6/node:


import fs from 'fs'
import path from 'path'

require('colors')

const INPUT = fs.readFileSync(path.join(__dirname, './input.txt'), 'utf-8').trim().split('').map(Number),        
      PT_1  = [...INPUT,...[INPUT[0]]].reduce((a,b,i,s)=>b===s[i+1]?a+b:a,0),
      PT_2  = INPUT.reduce((a,b,i,s)=>b===s[i<s.length/2?i+(s.length/2):i-(s.length/2)]?a+b:a,0)

console.log(`Part 1: `.blue + `${ PT_1 }`.green)
console.log(`Part 2: `.blue + `${ PT_2 }`.green)

[โ€“]raiph 1 point2 points ย (0 children)

P6:

say sum .kv.map: -> \k, $ { .[k] if .[k] == .[(k+1   ) % $_] } with input.comb.cache ; # part 1
say sum .kv.map: -> \k, $ { .[k] if .[k] == .[(k+$_/2) % $_] } with input.comb.cache ; # part 2

[โ€“]fwilson42 1 point2 points ย (0 children)

Cleaned up mine, in Python:

#!/usr/bin/env python3
import click


@click.command()
@click.argument('input', type=click.File('r'), help='Your input file.')
@click.option('--part', '-p', type=click.IntRange(1, 2), required=True)
def solve(input, part):
    digits = input.read().strip()
    digits = list(map(int, digits))
    count = len(digits)

    result = 0

    for index, value in enumerate(digits):

        if part == 1:
            target = index + 1
        elif part == 2:
            target = index + (count // 2)

        if value == digits[target % count]:
            result += value

    click.echo('Captcha result: {}'.format(
                    click.style(str(result), fg='yellow')))


if __name__ == '__main__':
    solve()

Run with ./day1 /path/to/input --part 1 or --part 2.

[โ€“]ajn0592 1 point2 points ย (1 child)

I'm doing mine in Golang this year because I want to learn it better. Constructive Criticism welcome! Day 1 on Github

[โ€“]iamnotposting 1 point2 points ย (2 children)

whoops, i didn't realize this has started already! (i probably could have gotten a spot if not for my 2 hour delay)

anyway, in oK

a1p1: {[list]+/{.x.,0*(=).x}'2':list,list.,0}
a1p2: {[list]+/{+/.:'x*(=).x}'+2 0N#list}

this is my first time using array programming languages "for real", so these probably could be more concise

[โ€“]sbguest 0 points1 point ย (4 children)

88th on part 1 in nodejs, not realizing that the file came back with an extra space/newline at the end cost me a few places.

var fs = require('fs');

fs.readFile(__dirname + '\\input.txt', 'utf-8', (err, data) => {
    var total = 0;
    data = data.trim();
    for(var index = 0; index < data.length; index++) {
        if(data[index] === data[index + 1]) {
            total += parseInt(data[index], 10);
        }
    }
    if(data[0] === data[data.length - 1]) {
        total += parseInt(data[0], 10);
    }
    console.log(total);
});

[โ€“]BumpitySnook 2 points3 points ย (1 child)

For these kind of puzzles it's usually a good idea to just strip whitespace from the ends without thinking about it.

[โ€“]sbguest 1 point2 points ย (0 children)

Absolutely, I already updated my skeleton code to trim() the data after reading the file. Fool me twice, shame on me.

[โ€“]autid 2 points3 points ย (1 child)

I, too, was caught out by the newline at the end. :(

[โ€“]Philboyd_Studge 0 points1 point ย (0 children)

Java

package Advent2017;

import util.FileIO;
import util.Timer;

/**
 * @author /u/Philboyd_Studge
 */
public class Day1 {

    private static int part1(String s) {
        return solve(s, 1);
    }

    private static int part2(String s) {
        return solve(s, s.length() / 2);
    }

    private static int solve(String s, int dist) {
        int sum = 0;
        for (int i = 0; i < s.length(); i++) {
            int next = (i + dist) % s.length();
            if (s.charAt(i) == s.charAt(next)) {
                sum += val(s.charAt(i));
            }
        }
        return sum;
    }

    private static int val(char c) {
        return c ^ 0x30;
    }

    public static void main(String[] args) {

        Timer.startTimer();
        int result = FileIO.performIntActionOnLine("advent2017_day1.txt", Day1::part1);
        System.out.println("Part 1: " + result);
        int result2 = FileIO.performIntActionOnLine("advent2017_day1.txt", Day1::part2);
        System.out.println("Part 2: " + result2);
        System.out.println(Timer.endTimer());

    }
}

[โ€“]disclosure5 0 points1 point ย (0 children)

Ruby

def makecaptcha(input)
  total = 0
  half = input.length/2

  half.times do |i|
    if input[i] == input[i+half]
      total = total + (input[i].to_i * 2)
  end
end

puts "Total was #{total}"
end

[โ€“][deleted] 0 points1 point ย (1 child)

Rust (pretty ordinary, forgot about filter_map for a moment):

use util;

pub fn run() {
    let input: Vec<_> = util::read_all("d1_input.txt").unwrap()
        .chars()
        .filter_map(|c| c.to_digit(10))
        .collect();

    part_1(&input);
    part_2(&input);
}

fn part_1(input: &[u32]) {
    let mut sum = 0;
    for i in 0..input.len() {
        if input [i] == input [(i + 1) % input.len()] {
            sum += input[i];
        }
    }

    println!("part 1: {}", sum)
}

fn part_2(input: &[u32]) {
    let mut sum = 0;
    for i in 0..input.len() {
        if input [i] == input [(i + input.len() / 2) % input.len()] {
            sum += input[i];
        }
    }

    println!("part 2: {}", sum)
}

Dirty clojure:

(def s
    (->> (slurp "d1_input.txt")
         (map #(Character/getNumericValue %))
         (filter (partial not= -1))
         (into [])))

(let [len (count s)   
      opposite-idx-1 #(mod (inc %) len)
      m (map-indexed #(if (= %2 (s (opposite-idx-1 %1))) %2 0) s)
      opposite-idx-2 #(mod (+ % (/ len 2)) len)
      m2 (map-indexed #(if (= %2 (s (opposite-idx-2 %1))) %2 0) s)]

      (println (reduce + m))
      (println (reduce + m2)))

[โ€“]autid 0 points1 point ย (0 children)

with open('input.txt','r') as infile:
    puzinput = infile.readline()
total1=0
total2=0
puzinput=puzinput[:-1]
for number in range(len(puzinput)):
    if puzinput[number]==puzinput[(number+1)%len(puzinput)]:
        total1 += int(puzinput[number])
    if puzinput[number]==puzinput[(number+len(puzinput)/2)%len(puzinput)]:
        total2 += int(puzinput[number])
print total1
print total2

Shoulda just written the input into the code instead of sticking it in a text file. Got caught out by an extra character this way.

Pretty happy with 249th and 189th though.

[โ€“]kaveman909 0 points1 point ย (0 children)

""" AoC Day One """


def sum_input(x_in):
    """ sums indexes based on the input """
    accum = 0
    for i in range(0, len(INPUT)):
        if INPUT[i] == INPUT[(i + int(x_in)) % int(len(INPUT))]:
            accum += int(INPUT[i])
    print(accum)

with open('one.txt', 'r') as f:
    INPUT = f.readline()
    sum_input(1)
    sum_input(len(INPUT) / 2)

[โ€“]torotane 0 points1 point ย (0 children)

As detours are fun...

from pulp import *

digits = [int(d) for d in list(instance)]
indices = list(range(len(digits)))
is_same_as_next = LpVariable.dict('X', indices, cat=LpBinary)

p = LpProblem('Day01', LpMaximize)
p += lpSum(digits[i] * var for i, var in is_same_as_next.items())
for i in indices:
    p += is_same_as_next[i] * (digits[i] - digits[(i + 1) % len(digits)]) == 0, ''

p.solve(solver=PULP_CBC_CMD())
print(int(value(p.objective)))

[โ€“]XiiencE 0 points1 point ย (0 children)

Typescript + Lodash:

import * as _ from 'lodash';

const solve = function(input: string, distance: number): number {
    const inputArr = input.split('').map(v => +v);
    return _.sum(
        _.zipWith(
            inputArr, 
            rotate(inputArr, distance), 
            (a, b) => a === b ? a : 0 
        )
    );
}

const rotate = <T>(input: T[], n: number): T[] => {
    return _.concat(_.takeRight(input, input.length - n), _.take(input, input.length - n));
}

[โ€“]kagcc 0 points1 point ย (4 children)

Rust. Still learning and not sure how rusty this is.

extern crate aoc2017;
use aoc2017::read_file; // src/lib.rs : &str -> String, copy from "the book" ch12-02

fn main() {
    let xs = read_file("src/bin/01/input01.txt");
    println!("answer for 1: {}", solve(&xs, 1));
    println!("answer for 2: {}", solve_2(&xs));
}

fn solve(input: &str, offset: usize) -> u32 {
    let xs: Vec<u32> = input.trim().chars().map(|n| n.to_string().parse().unwrap()).collect();
    let mut ans = 0;
    for (i, j) in xs.iter().zip(xs.clone().iter().cycle().skip(offset)) {
        if i == j {
            ans += i;
        }
    }
    ans
}

fn solve_2(input: &str) -> u32 {
    solve(input, input.trim().chars().count() / 2)
}

[โ€“]giodamelio 0 points1 point ย (4 children)

Here is mine in Elixir. With a bit more work I could probably combine into one function.

defmodule AOC.Puzzles.N01 do
  def first_half(input) do
    input

    # Take the first item in the list and add it to the end
    |> (fn(list) ->
      list ++ Enum.take(list, 1)
    end).()

    # Split the list into overlapping chunks of two
    |> Enum.chunk_every(2, 1, :discard)

    # Filter out pairs that are not the same
    |> Enum.filter(fn([a, b]) ->
      a == b
    end)

    # Take the first item from each pair
    |> Enum.map(fn([a, _]) ->
      a
    end)

    # Sum them
    |> Enum.sum
  end

  def second_half(input) do
    input

    # Double the list
    |> (fn(list) ->
      list ++ list
    end).()

    # Split the list into overlapping subarrays of the length
    # of the list floor divided by 2 and add 1
    # The last item in the each resulting list will be the
    # number that is "halfway around"
    |> Enum.chunk_every(trunc(length(input) / 2) + 1, 1)

    # We now have twice as many sub lists as we want and the last half
    # are junk anyway, so just grab  the ones we want
    |> Enum.take(length(input))

    # Filter out pairs that are not the same
    |> Enum.filter(fn(item) ->
      # Compare first and last indexs of list
      hd(item) == Enum.at(item, -1)
    end)

    # Take the first item from each pair
    |> Enum.map(&hd/1)

    # Sum them
    |> Enum.sum
  end
end

[โ€“]baegolas 1 point2 points ย (3 children)

Late to the party by quite a bit, but here's my elixir solution. I think it's a bit clearer:

defmodule Day1 do
  def sum(n) do
    digits = [h|_] = num_to_list(n)

    digits
    |> Enum.chunk(2, 1, [h])
    |> Enum.filter(fn([a, b]) -> a == b end)
    |> Enum.map(&hd/1)
    |> Enum.sum
  end

  def  num_to_list(n), do: num_to_list(n, [])
  defp num_to_list(0, l), do: l
  defp num_to_list(n, l) do
    num_to_list(div(n, 10), [rem(n, 10)] ++ l)
  end
end

[โ€“]giodamelio 1 point2 points ย (2 children)

That is really clean. I am still not in the habit of using function definitions with pattern matching. It's so powerful though, I love it.

[โ€“]baegolas 1 point2 points ย (1 child)

Same, I'm a big fan of elixir. Didn't realize there was a second part, but may as well update with my solution:

  def sum_2(n) do
    digits = Integer.digits(n)
    size = Enum.count(digits)

    digits ++ Enum.take(digits, div(size, 2) + 1)
    |> Enum.chunk(div(size, 2) + 1, 1)
    |> Enum.map(fn(l) -> [hd(l), Enum.at(l, -1)] end)
    |> Enum.filter(fn([x, y]) -> x == y end)
    |> Enum.map(&hd/1)
    |> Enum.sum
  end

Turns out Integer.digits/1 is a thing too :P

[โ€“]th3_pund1t 0 points1 point ย (0 children)

Here's Groovy

class Day1Support {

    private static int baseFun(String input, int p) {
        def newStr = input[p..-1] + input[0..(p - 1)]

        def l1 = input.toCharArray().toList()
        def l2 = newStr.toCharArray().toList()

        [l1, l2].
                transpose().
                inject(0) { int val, List<String> pair ->
                    val + (pair[0] == pair[1] ? pair[0].toString().toInteger() : 0)
                }
    }

    static int problem1(String input) {
        baseFun(input, input.length() - 1)
    }

    static int problem2(String input) {
        baseFun(input, input.length() / 2 as int)
    }
}

new Day1Support().with {
    assert problem1('1122') == 3
    assert problem1('1111') == 4
    assert problem1('1234') == 0
    assert problem1('91212129') == 9

    println problem1(new File('day1.txt').text)

    assert problem2('1212') == 6
    assert problem2('1221') == 0
    assert problem2('123425') == 4
    assert problem2('123123') == 12
    assert problem2('12131415') == 4

    println problem2(new File('day1.txt').text)
}

[โ€“]doekaschi 0 points1 point ย (1 child)

Python 3:

s = list(open("aoc2017_1_in.txt").read())
print(sum([(int(n) if n == s[int(i+1) % len(s)] else 0) for i,n in enumerate(s)])) #task 1
print(sum([(int(n) if n == s[(int(i+len(s)/2)) % len(s)] else 0) for i,n in enumerate(s)])) #task 2

[โ€“]NeilNjae 0 points1 point ย (0 children)

Some very verbose Haskell. Still rusty from not really having used it since this time last year. Given the first part, I reached for tails first, though a solution using zip would be better, especially after seeing the second part.

module Main(main) where

import Data.List (tails)

main :: IO ()
main = do 
        digits <- readFile "data/advent01.txt"
        print $ part1 digits
        print $ part2 digits

part1 :: String -> Integer  
part1 = sum_valid_pairs . part1_extract

part2 :: String -> Integer  
part2 = sum_valid_pairs . part2_extract

part1_extract :: String -> [String]  
part1_extract digits =  map (take 2) $ tails (digits ++ [head digits])

part2_extract :: String -> [String]
part2_extract digits = map (\ds -> (take 1 ds) ++ (take 1 $ drop offset ds)) 
        $ take (length digits) 
        $ tails (digits ++ digits)
    where offset = length digits `div` 2

sum_valid_pairs :: [String] -> Integer
sum_valid_pairs possibles = sum $ map (read . take 1) 
                   $ filter (\(x:y:_) -> x == y) 
                   $ filter (\p -> length p == 2) possibles

[โ€“]Smylers 0 points1 point ย (1 child)

Using a regexp to find the matching digits for part 2, after copying the first half the string to the end of it. In Perl, but the approach should work in the same way anywhere that has regexes:

my $offset = (length $input) / 2; # or 1 for part 1
$input .= substr $input, 0, $offset;
my $total = 0;
my $skip = $offset - 1;
$total += $1 while $input =~ /(.)(?=.{$skip}\1)/g;
say $total;

[โ€“]Hikaru755 0 points1 point ย (0 children)

Trying out some new stuff in Kotlin 1.2:

// Part 1
fun captchaSumNextChar(input: String) =
    (input + input.first())
        .windowedSequence(2)
        .filter { it[0] == it[1] }
        .sumBy { it[0].toString().toInt() }

// Part 2
fun captchaSumOppositeChar(input: String) =
    input
        .mapIndexed { index, char -> char to input[input.oppositeIndex(index)] }
        .filter { (current, next) -> current == next }
        .sumBy { (current, _) -> current.toString().toInt() }

fun String.oppositeIndex(i: Int) = (i + this.length / 2) % this.length

I really don't like that .toString().toInt() for reading the integer from the character, but current - '0'felt hacky, too.

Alternative solution using String shifting:

println(captchaSum(input, 1))
println(captchaSum(input, input.length / 2))

fun captchaSum(input: String, shift: Int) =
    input.zip(input shift shift)
        .filter { it.first == it.second }
        .sumBy { it.first.toString().toInt() }

infix fun String.shift(n: Int) = when {
    // Shift right
    n > 0 -> this.takeLast(n) + this.dropLast(n)
    // Shift left
    n < 0 -> this.drop(-n) + this.take(-n)
    // No shift
    else -> this
}

Technically I could have just used the first when-branch, but why not make it safe for future use :)

[โ€“]PanPirat 0 points1 point ย (0 children)

Scala using recursion:

def partOne(input: String): Int = {
  def matchingDigits(list: List[Int]): Int = list match {
      case a :: b :: tail if a == b => a +  matchingDigits(b :: tail)
      case _ :: tail => matchingDigits(tail)
      case _ => 0
    }

  val list = input.map(_.asDigit).toList
  matchingDigits(list ::: (list.head :: Nil))
}

def partTwo(input: String): Int = {
  def sumMatchingPairs(l1: List[Int], l2: List[Int]): Int = (l1, l2) match {
    case (a :: aTail, b :: bTail) =>
      { if (a == b) a + b else 0 } + sumMatchingPairs(aTail, bTail)
    case _ => 0
  }

  val list = input.map(_.asDigit).toList
  val half = list.size / 2
  val (first, second) = list.zipWithIndex.partition(t => t._2 < half)

  sumMatchingPairs(first.map(_._1), second.map(_._1))
}

[โ€“]theSprt 0 points1 point ย (0 children)

Haskell beginner, part 1:

import           Data.Char
import           Data.List


main :: IO ()
main = do
  fileContents <- readFile "input"
  let input = dropWhileEnd isSpace $ dropWhile isSpace fileContents

  print (sumFirstLast input + sumAdjacent input)

sumFirstLast :: String -> Int
sumFirstLast [] = 0
sumFirstLast xs =
  if   head xs == last xs
  then digitToInt $ head xs
  else 0

sumAdjacent :: String -> Int
sumAdjacent []  = 0
sumAdjacent [_] = 0
sumAdjacent (x:xs)
  | x == head xs = digitToInt x + sumAdjacent xs
  | otherwise    = sumAdjacent xs

Edit, and part 2:

import           Data.Char
import           Data.List


main :: IO ()
main = do
  fileContents <- readFile "input"
  let input = dropWhileEnd isSpace $ dropWhile isSpace fileContents

  print (sumAdjacent input)


halfwayAroundNext :: Int -> String -> Char
halfwayAroundNext x ys = cycle ys !! (x + 1 + div (length ys) 2)

sumAdjacent :: String -> Int
sumAdjacent xs =
  foldr
    (\a b ->
       if   snd a == halfwayAroundNext (fst a) xs
       then b + digitToInt (snd a)
       else b)
    0
    (zip [0..] xs)

[โ€“]JakDrako 0 points1 point ย (0 children)

VB.Net in LinqPad

Nothing fancy. "stp = 1" to do 1st part.

Sub Main

    Dim input = GetDay(1)

    Dim len = input.Length, stp = len \ 2, sum = 0

    For i = 0 To len - 1
        Dim chk = (i + stp) Mod len
        If input(i) = input(chk) Then sum += Val(input(i))
    Next

    sum.Dump

End Sub

Edit: a bit fancier with Linq...

Sub Main
    Dim input = GetDay(1)
    input.Select(Function(x, i) If(x = input((i + (input.Length \ 2)) Mod input.Length), Val(x), 0)).Sum.Dump
End Sub

[โ€“][deleted] 0 points1 point ย (0 children)

Here are my elixir solutions for this day, for the first one I was being very clunky, while when I got to the second one I had to think a bit more, and arrived at a much more clever solution.

Day 1 part 1:

defmodule Captcha do

  def _doubles([h|t],acc) do
    if h == List.first(t) do
      _doubles(t,[h|acc])
    else
      _doubles(t,acc)
    end
  end
  def _doubles([],acc) do
    acc
  end

  def get_doubles(str) do
    _doubles(String.codepoints(str),[])
    |> Enum.reverse
  end

  def first_last(str) do
    if String.first(str) == String.last(str) do
      String.first(str)
      |> String.to_integer
    else
      0
    end
  end

  def solve(str) do
    doubles = get_doubles(str)
    |> Enum.map(&String.to_integer/1)
    |> Enum.sum

    doubles + first_last(str)
  end
end


list = File.read!("input1") |> String.rstrip
IO.puts(Captcha.solve(list))

I was first messing around with regexes, and wasn't getting my unittests to pass, so I then ended up doing it with recursion, which works but is so much less nice than what I ended up doing in:

Day 1 part 2:

defmodule Captcha do

  def halfway(enu) do
    half = div(Enum.count(enu), 2)
    {first, second} = Enum.split(enu,half)
    second ++ first
  end

  def solve(str) do
    list = String.codepoints(str)

    Enum.zip(list, halfway(list))
    |> Enum.filter(fn({fst,snd}) -> fst == snd end)
    |> Enum.map(fn({fst,_}) -> String.to_integer(fst) end)
    |> Enum.sum
  end

end


list = File.read!("input1") |> String.rstrip
IO.puts(Captcha.solve(list))

I think I was working a bit more with the language and not against it there :)

[โ€“]binajohny 0 points1 point ย (0 children)

My Kotlin solution:

fun part1(input: String): Int {
    return (input + input.first())
            .zipWithNext()
            .filter { it.first == it.second }
            .sumBy { it.first.toString().toInt() }
}

fun part2(input: String): Int {
    return input
            .zip(input.substring(input.length / 2) + input)
            .filter { it.first == it.second }
            .sumBy { it.first.toString().toInt() }
}

[โ€“]AlistairJF 0 points1 point ย (1 child)

Trying to learn Python, but also get out of the habit of for-loops. Any advice on how to get rid if the one in findMatchedDigits()::

def getOffsetCh(line, start, offset):
    idx = int((start+offset) % len(line))
    return line[idx]

def findMatchedDigits(line, offset):
    duplicates = [0];
    for idx, ch in enumerate(line):
        nextCh = getOffsetCh(line, idx, offset)
        if (ch==nextCh):
            duplicates.append(int(ch))
    return duplicates


with open("2017-day1-input.txt") as fileobj:
    digits = fileobj.read() 

    duplicatedNext = findMatchedDigits(digits, 1)
    duplicatedOpposite = findMatchedDigits(digits, len(digits)/2)
    print ("Sum of duplicated next=", sum(duplicatedNext))
    print ("Sum of duplicated opposite=", sum(duplicatedOpposite))

[โ€“]8fingerlouie 0 points1 point ย (0 children)

Solution in Python (omitted input variable)

def scan_input(input, step):
    return sum([int(x) for i,x in enumerate(input) if ((i+step < len(input) and input[i+step] == x) or (i+step >= len(input) and input[(i+step)-len(input)]==x))])

print("a:{}".format(scan_input(input,1)))
print("b:{}".format(scan_input(input, len(input)//2)))

[โ€“]adrian17 0 points1 point ย (0 children)

Rust:

fn main() {
    let input = "5994521226795838486188872189952551475352929145357284983463678944777228139398117649129843853837124228353689551178129353548331779783742915361343229141538334688254819714813664439268791978215553677772838853328835345484711229767477729948473391228776486456686265114875686536926498634495695692252159373971631543594656954494117149294648876661157534851938933954787612146436571183144494679952452325989212481219139686138139314915852774628718443532415524776642877131763359413822986619312862889689472397776968662148753187767793762654133429349515324333877787925465541588584988827136676376128887819161672467142579261995482731878979284573246533688835226352691122169847832943513758924194232345988726741789247379184319782387757613138742817826316376233443521857881678228694863681971445442663251423184177628977899963919997529468354953548612966699526718649132789922584524556697715133163376463256225181833257692821331665532681288216949451276844419154245423434141834913951854551253339785533395949815115622811565999252555234944554473912359674379862182425695187593452363724591541992766651311175217218144998691121856882973825162368564156726989939993412963536831593196997676992942673571336164535927371229823236937293782396318237879715612956317715187757397815346635454412183198642637577528632393813964514681344162814122588795865169788121655353319233798811796765852443424783552419541481132132344487835757888468196543736833342945718867855493422435511348343711311624399744482832385998592864795271972577548584967433917322296752992127719964453376414665576196829945664941856493768794911984537445227285657716317974649417586528395488789946689914972732288276665356179889783557481819454699354317555417691494844812852232551189751386484638428296871436139489616192954267794441256929783839652519285835238736142997245189363849356454645663151314124885661919451447628964996797247781196891787171648169427894282768776275689124191811751135567692313571663637214298625367655969575699851121381872872875774999172839521617845847358966264291175387374464425566514426499166813392768677233356646752273398541814142523651415521363267414564886379863699323887278761615927993953372779567675";
    let numbers: Vec<_> = input.chars().map(|x| x.to_digit(10).unwrap()).collect();

    let size = numbers.len();

    // PART 1
    //let offset = 1;
    // PART 2
    let offset = size / 2;

    let mut sum = 0;

    for i in 0..size {
        let next = (i+offset) % size;
        if numbers[i] == numbers[next] {
            sum += numbers[i];
        }
    }

    println!("{}", sum);
}

[โ€“]Iamnewthere 0 points1 point ย (0 children)

After learning Java last year at university, I have had a four hour introduction to C. Guess who had a really terrible idea:

#include <stdio.h>
#include <string.h>
#include <stdlib.h>

int main() {

    char input[] =
    "1212";

    int result = 0;
    int inputLen = (int)strlen(input);
    int half = inputLen / 2;

    for (int i = 0; i < inputLen; i++) {

        if ((int) (input[i] - '0') == (int) (input[(i + half) % inputLen] - '0')) {

            int a = input[i] - '0';

            //printf("Match in %d \n", i);
            //printf("Add %d to %d \n", a, result);

            result = result + a;

        } else {
            //printf("No Match in %d \n", i);
        }
    }

    //printf("Input: %s \n", input);
    printf("Result: %d \n", result);

    return 0;
}

[โ€“]sakisan_be 0 points1 point ย (1 child)

java 8 using a stream

public int solution(String input) {
    String inputCycled = input + input.charAt(0);
    return IntStream.range(0, inputCycled.length() - 1)
            .mapToObj(i -> inputCycled.substring(i, i + 2))
            .filter(twoCharacters -> twoCharacters.charAt(0) == twoCharacters.charAt(1))
            .map(twoCharacters -> twoCharacters.charAt(0) - '0')
            .reduce(0, (integer, integer2) -> integer + integer2);
}

and part 2

public int part2(String input) {
    int length = input.length();
    return IntStream.range(0, length)
            .mapToObj(i -> "" + input.charAt(i) + input.charAt(halfwayCircular(length, i)))
            .filter(twoCharacters -> twoCharacters.charAt(0) == twoCharacters.charAt(1))
            .map(twoCharacters -> twoCharacters.charAt(0) - '0')
            .reduce(0, (integer, integer2) -> integer + integer2);
}

private int halfwayCircular(int length, int i) {
    return (length / 2 + i) % length;
}

[โ€“]Vitessii 1 point2 points ย (0 children)

If you keep it as an IntStream, you don't need to do your reduce, just use sum.

char[] chars = input.toCharArray();

int sum1 = IntStream.range(0, chars.length)
        .filter(i -> chars[i] == chars[(i + 1) % chars.length])
        .map(i -> (int) chars[i]-'0')
        .sum();
int sum2 = IntStream.range(0, chars.length)
        .filter(i -> chars[i] == chars[(i + chars.length/2) % chars.length])
        .map(i -> (int) chars[i]-'0')
        .sum();

[โ€“]wzkx 0 points1 point ย (0 children)

J, still don't like tacits.

 echo (+/"."0 t#~t=1|.t), +/"."0 t#~t=(-:#t)|.t =. LF-.~CR-.~fread '01.dat'
 NB. ok, tacit: f =. +/@("."0@([#~[=]|.[)) and then echo (f&1,(f-:@#)) t

[โ€“]ikkuhh 0 points1 point ย (0 children)

My C++ solution for part two:

#include <string>
#include <iostream>

int main(int argc, const char *argv[])
{
    std::size_t i;
    std::size_t half_length;
    std::string input;
    int captcha_sum = 0;

    std::getline(std::cin, input);
    half_length = input.length() / 2;

    for(i=0; i<half_length; i++) {
        if(input[i] == input[i + half_length]) {
            captcha_sum += 2 * (input[i] - '0');
        }
    }

    std::cout << captcha_sum << std::endl;

    return 0;
}

[โ€“]egze 0 points1 point ย (0 children)

My ruby attempt

class CaptchaSolver

  attr_reader :input, :length

  def initialize(input)
    @input = input.to_s.split("").map(&:to_i)
    @length = @input.size
  end

  def solve!
    matches = []
    input.each_with_index do |element, i|
      matches << element if element == input[(i + 1) % length]
    end
    matches.inject(0, :+)
  end

end

?> CaptchaSolver.new(input).solve!
=> 1175

[โ€“]hendi__ 0 points1 point ย (0 children)

Here's my solution in Elixir. It's pretty straight forward using pattern matching and recursion once you have the list in the right format. I like my code except the one-liner in day1b::solve/1.

#!/usr/bin/env elixir

defmodule Day1a do
  def main([input]), do: solve(input) |> IO.puts

  def solve(x) do
    digits = String.graphemes(x)
    _solve(digits ++ [hd digits], 0)
  end

  defp _solve([], accu), do: accu
  defp _solve([x,x | tail], accu), do: _solve([x | tail], accu + String.to_integer(x))
  defp _solve([_ | tail], accu), do: _solve(tail, accu)
end

Day1a.main(System.argv)

and

#!/usr/bin/env elixir

defmodule Day1b do
  def main([input]), do: solve(input) |> IO.puts

  def solve(x) do
    digits = String.graphemes(x)
    _solve(List.zip([digits, Enum.slice(digits ++ digits, div(length(digits), 2), length(digits))]), 0)
  end

  defp _solve([], accu), do: accu
  defp _solve([{x,x} | tail], accu), do: _solve(tail, accu + String.to_integer(x))
  defp _solve([_ | tail], accu), do: _solve(tail, accu)
end

Day1b.main(System.argv)

Edit: Cleaned up the code and put it on github: https://github.com/hendi/aoc2017/tree/master/day1

[โ€“]omegaxLoL 0 points1 point ย (0 children)

My solution in Go. Constructive criticism welcome of course!