├── 2015 ├── day01 │ └── code.py ├── day02 │ └── code.py ├── day03 │ └── code.py ├── day04 │ └── code.py ├── day05 │ └── code.py ├── day06 │ └── code.py ├── day07 │ └── code.py ├── day08 │ └── code.py ├── day09 │ └── code.py ├── day10 │ └── code.py ├── day11 │ └── code.py ├── day12 │ └── code.py ├── day13 │ └── code.py ├── day14 │ └── code.py ├── day15 │ └── code.py ├── day16 │ └── code.py ├── day17 │ └── code.py ├── day18 │ └── code.py ├── day19 │ └── code.py ├── day20 │ └── code.py ├── day21 │ └── code.py ├── day22 │ └── code.py ├── day23 │ └── code.py ├── day24 │ └── code.py └── day25 │ └── code.py ├── 2016 ├── day01 │ └── code.py ├── day02 │ └── code.py ├── day03 │ └── code.py ├── day04 │ └── code.py ├── day05 │ └── code.py ├── day06 │ └── code.py ├── day07 │ └── code.py ├── day08 │ └── code.py ├── day09 │ └── code.py ├── day10 │ └── code.py ├── day11 │ └── code.py ├── day12 │ └── code.py ├── day13 │ └── code.py ├── day14 │ └── code.py ├── day15 │ └── code.py ├── day16 │ └── code.py ├── day17 │ └── code.py ├── day18 │ └── code.py ├── day19 │ └── code.py ├── day20 │ └── code.py ├── day21 │ └── code.py ├── day22 │ └── code.py ├── day23 │ └── code.py ├── day24 │ └── code.py └── day25 │ └── code.py ├── 2017 ├── day01 │ └── code.py ├── day02 │ └── code.py ├── day03 │ └── code.py ├── day04 │ └── code.py ├── day05 │ └── code.py ├── day06 │ └── code.py ├── day07 │ └── code.py ├── day08 │ └── code.py ├── day09 │ └── code.py ├── day10 │ └── code.py ├── day11 │ └── code.py ├── day12 │ └── code.py ├── day13 │ └── code.py ├── day14 │ └── code.py ├── day15 │ └── code.py ├── day16 │ └── code.py ├── day17 │ └── code.py ├── day18 │ └── code.py ├── day19 │ └── code.py ├── day20 │ └── code.py ├── day21 │ └── code.py ├── day22 │ └── code.py ├── day23 │ └── code.py ├── day24 │ └── code.py └── day25 │ └── code.py ├── 2018 ├── CMakeLists.txt ├── day01 │ ├── CMakeLists.txt │ └── day01.cpp ├── day02 │ ├── CMakeLists.txt │ └── day02.cpp ├── day03 │ └── code.py ├── day04 │ └── code.py ├── day05 │ └── code.py ├── day06 │ └── code.py ├── day07 │ └── code.py ├── day08 │ └── code.py ├── day09 │ └── code.py ├── day10 │ └── code.py ├── day11 │ └── code.py ├── day12 │ └── code.py ├── day13 │ └── code.py ├── day14 │ └── code.py ├── day15 │ └── code.py ├── day16 │ └── code.py ├── day17 │ └── code.py ├── day18 │ └── code.py ├── day19 │ └── code.py ├── day20 │ └── code.py ├── day21 │ └── code.py ├── day22 │ └── code.py ├── day23 │ └── code.py ├── day24 │ └── code.py └── day25 │ └── code.py ├── 2019 ├── CMakeLists.txt ├── day01 │ ├── CMakeLists.txt │ ├── day.cpp │ └── day1.go ├── day02 │ ├── CMakeLists.txt │ └── day.cpp ├── day03 │ ├── CMakeLists.txt │ └── day.cpp ├── day04 │ ├── CMakeLists.txt │ └── day.cpp ├── day05 │ ├── CMakeLists.txt │ └── day.cpp ├── day06 │ ├── CMakeLists.txt │ └── day.cpp ├── day07 │ ├── CMakeLists.txt │ └── day.cpp ├── day08 │ ├── CMakeLists.txt │ └── day.cpp ├── day09 │ ├── CMakeLists.txt │ └── day.cpp ├── day10 │ ├── CMakeLists.txt │ └── day10.cpp ├── day11 │ ├── CMakeLists.txt │ └── day11.cpp ├── day12 │ ├── CMakeLists.txt │ └── day12.cpp ├── day13 │ ├── CMakeLists.txt │ └── day13.cpp ├── day14 │ ├── CMakeLists.txt │ └── day14.cpp ├── day15 │ ├── CMakeLists.txt │ └── day15.cpp ├── day16 │ ├── CMakeLists.txt │ └── day16.cpp ├── day17 │ ├── CMakeLists.txt │ └── day17.cpp ├── day18 │ ├── CMakeLists.txt │ └── day18.cpp ├── day19 │ ├── CMakeLists.txt │ └── day19.cpp ├── day20 │ ├── CMakeLists.txt │ ├── code.py │ └── day20.cpp ├── day21 │ ├── CMakeLists.txt │ └── day21.cpp ├── day22 │ ├── CMakeLists.txt │ └── day22.cpp ├── day23 │ ├── CMakeLists.txt │ └── day23.cpp ├── day24 │ ├── CMakeLists.txt │ └── day24.cpp ├── day25 │ ├── CMakeLists.txt │ └── day25.cpp └── dayxx │ ├── CMakeLists.txt │ └── dayxx.cpp ├── 2020 ├── .gitignore ├── day01 │ └── code.py ├── day02 │ └── code.py ├── day03 │ └── code.py ├── day04 │ └── code.py ├── day05 │ └── code.py ├── day06 │ └── code.py ├── day07 │ └── code.py ├── day08 │ └── code.py ├── day09 │ └── code.py ├── day10 │ └── code.py ├── day11 │ └── code.py ├── day12 │ └── code.py ├── day13 │ └── code.py ├── day14 │ └── code.py ├── day15 │ └── code.py ├── day16 │ └── code.py ├── day17 │ └── code.py ├── day18 │ └── code.py ├── day19 │ └── code.py ├── day20 │ ├── code.py │ ├── monster.txt │ └── output.txt ├── day21 │ └── code.py ├── day22 │ └── code.py ├── day23 │ └── code.py ├── day24 │ └── code.py ├── day25 │ └── code.py └── init2020.py ├── 2021 ├── .gitignore ├── Cargo.toml ├── day01 │ ├── code.py │ └── main.rs ├── day02 │ ├── code.py │ └── main.rs ├── day03 │ ├── code.py │ └── main.rs ├── day04 │ ├── code.py │ └── main.rs ├── day05 │ ├── code.py │ └── main.rs ├── day06 │ ├── code.py │ └── main.rs ├── day07 │ ├── code.py │ └── main.rs ├── day08 │ ├── code.py │ └── main.rs ├── day09 │ ├── code.py │ └── main.rs ├── day10 │ ├── code.py │ └── main.rs ├── day11 │ ├── code.py │ └── main.rs ├── day12 │ ├── code.py │ └── main.rs ├── day13 │ ├── code.py │ └── main.rs ├── day14 │ ├── code.py │ └── main.rs ├── day15 │ ├── code.py │ └── main.rs ├── day16 │ ├── code.py │ └── main.rs ├── day17 │ ├── code.py │ └── main.rs ├── day18 │ ├── code.py │ └── main.rs ├── day19 │ ├── code.py │ └── main.rs ├── day20 │ ├── code.py │ └── main.rs ├── day21 │ ├── code.py │ └── main.rs ├── day22 │ ├── code.py │ └── main.rs ├── day23 │ └── code.py ├── day24 │ ├── code.py │ └── main.rs ├── day25 │ ├── code.py │ └── main.rs └── template │ ├── code.py │ └── main.rs ├── 2022 ├── .gitignore ├── Cargo.toml ├── day01 │ ├── code.py │ └── main.rs ├── day02 │ ├── code.py │ └── main.rs ├── day03 │ ├── code.py │ └── main.rs ├── day04 │ ├── code.py │ └── main.rs ├── day05 │ ├── code.py │ └── main.rs ├── day06 │ ├── code.py │ └── main.rs ├── day07 │ ├── code.py │ └── main.rs ├── day08 │ ├── code.py │ └── main.rs ├── day09 │ ├── code.py │ └── main.rs ├── day10 │ ├── code.py │ └── main.rs ├── day11 │ ├── code.py │ └── main.rs ├── day12 │ ├── code.py │ └── main.rs ├── day13 │ ├── code.py │ └── main.rs ├── day14 │ ├── code.py │ └── main.rs ├── day15 │ ├── code.py │ └── main.rs ├── day16 │ ├── code.py │ └── main.rs ├── day17 │ ├── code.py │ └── main.rs ├── day18 │ ├── code.py │ └── main.rs ├── day19 │ ├── code.py │ └── main.rs ├── day20 │ ├── code.py │ └── main.rs ├── day21 │ ├── code.py │ └── main.rs ├── day22 │ ├── code.py │ └── main.rs ├── day23 │ ├── code.py │ └── main.rs ├── day24 │ ├── code.py │ └── main.rs ├── day25 │ ├── code.py │ └── main.rs └── template │ ├── code.py │ └── main.rs ├── 2023 ├── Cargo.toml ├── day01 │ ├── code.py │ └── main.rs ├── day02 │ ├── code.py │ └── main.rs ├── day03 │ ├── code.py │ └── main.rs ├── day04 │ ├── code.py │ └── main.rs ├── day05 │ ├── code.py │ └── main.rs ├── day06 │ ├── code.py │ └── main.rs ├── day07 │ ├── code.py │ └── main.rs ├── day08 │ ├── code.py │ └── main.rs ├── day09 │ ├── code.py │ └── main.rs ├── day10 │ └── code.py ├── day11 │ └── code.py ├── day12 │ ├── code.py │ └── main.rs ├── day13 │ └── code.py ├── day14 │ └── code.py ├── day15 │ └── code.py ├── day16 │ └── code.py ├── day17 │ └── code.py ├── day18 │ ├── code.py │ └── main.rs ├── day19 │ └── code.py ├── day20 │ └── code.py ├── day21 │ └── code.py ├── day22 │ └── code.py ├── day23 │ ├── code.py │ └── main.rs ├── day24 │ └── code.py ├── day25 │ ├── code.py │ └── main.rs └── template │ ├── code.py │ └── main.rs ├── 2024 ├── Cargo.toml ├── create_template.py ├── day01 │ ├── code.py │ └── main.rs ├── day02 │ ├── code.py │ └── main.rs ├── day03 │ ├── code.py │ └── main.rs ├── day04 │ ├── code.py │ └── main.rs ├── day05 │ ├── code.py │ └── main.rs ├── day06 │ ├── code.py │ └── main.rs ├── day07 │ ├── code.py │ └── main.rs ├── day08 │ ├── code.py │ └── main.rs ├── day09 │ ├── code.py │ └── main.rs ├── day10 │ ├── code.py │ └── main.rs ├── day11 │ ├── code.py │ └── main.rs ├── day12 │ ├── code.py │ └── main.rs ├── day13 │ ├── code.py │ └── main.rs ├── day14 │ ├── code.py │ └── main.rs ├── day15 │ ├── code.py │ ├── main.rs │ └── test_corner.txt ├── day16 │ ├── code.py │ └── main.rs ├── day17 │ ├── code.py │ └── main.rs ├── day18 │ ├── code.py │ └── main.rs ├── day19 │ ├── code.py │ └── main.rs ├── day20 │ ├── code.py │ └── main.rs ├── day21 │ ├── code.py │ └── main.rs ├── day22 │ ├── code.py │ └── main.rs ├── day23 │ ├── code.py │ └── main.rs ├── day24 │ ├── code.py │ └── main.rs ├── day25 │ ├── code.py │ └── main.rs └── template │ ├── code.py │ └── main.rs ├── 2025 ├── Cargo.toml ├── benches.rs └── template │ ├── code.py │ └── mod.rs ├── .devcontainer ├── Dockerfile └── devcontainer.json ├── .github └── workflows │ └── lint.yml ├── .gitignore ├── .pylintrc ├── CMakeLists.txt ├── LICENSE ├── README.md └── check.py /.devcontainer/Dockerfile: -------------------------------------------------------------------------------- 1 | 2 | FROM ubuntu:22.04 3 | FROM rust:1.65 4 | 5 | ENV TZ="Europe/Berlin" 6 | 7 | RUN apt update && \ 8 | apt install -y git python3 cmake curl 9 | -------------------------------------------------------------------------------- /.devcontainer/devcontainer.json: -------------------------------------------------------------------------------- 1 | { 2 | "build": { 3 | "dockerfile": "Dockerfile", 4 | }, 5 | // Set *default* container specific settings.json values on container create. 6 | "settings": { 7 | "python.pythonPath": "/usr/local/bin/python", 8 | "python.languageServer": "Pylance", 9 | "python.linting.enabled": true, 10 | "python.linting.pylintEnabled": true, 11 | "python.formatting.autopep8Path": "/usr/local/py-utils/bin/autopep8", 12 | "python.formatting.blackPath": "/usr/local/py-utils/bin/black", 13 | "python.formatting.yapfPath": "/usr/local/py-utils/bin/yapf", 14 | "python.linting.banditPath": "/usr/local/py-utils/bin/bandit", 15 | "python.linting.flake8Path": "/usr/local/py-utils/bin/flake8", 16 | "python.linting.mypyPath": "/usr/local/py-utils/bin/mypy", 17 | "python.linting.pycodestylePath": "/usr/local/py-utils/bin/pycodestyle", 18 | "python.linting.pydocstylePath": "/usr/local/py-utils/bin/pydocstyle", 19 | "python.linting.pylintPath": "/usr/local/py-utils/bin/pylint" 20 | }, 21 | // Add the IDs of extensions you want installed when the container is created. 22 | "extensions": [ 23 | "ms-python.python", 24 | "ms-python.vscode-pylance" 25 | ], 26 | } -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | .vs/* 2 | **build/ 3 | CMakeSettings.json 4 | out/ 5 | **/target/* 6 | *Cargo.lock 7 | **input.txt 8 | **.vscode/* 9 | *DS_STORE 10 | -------------------------------------------------------------------------------- /.pylintrc: -------------------------------------------------------------------------------- 1 | [MAIN] 2 | disable=C0114,C0116,C0301,C0209,W1514,C0414,E0001 3 | -------------------------------------------------------------------------------- /2015/day01/code.py: -------------------------------------------------------------------------------- 1 | import time,os 2 | 3 | def profiler(method): 4 | def wrapper_method(*arg, **kw): 5 | t = time.time() 6 | method(*arg, **kw) 7 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 8 | return wrapper_method 9 | 10 | @profiler 11 | def part1(): 12 | 13 | with open('input.txt', 'r') as f_in : 14 | ls = f_in.read().strip() 15 | print(ls.count('(') - ls.count(')')) 16 | 17 | 18 | 19 | @profiler 20 | def part2(): 21 | with open('input.txt', 'r') as f_in : 22 | ls = f_in.read().strip() 23 | floor = 0 24 | for idx,ch in enumerate(ls): 25 | if ch == '(' : floor += 1 26 | elif ch == ')' : floor -=1 27 | 28 | if floor == -1 : 29 | print(idx + 1) 30 | break 31 | 32 | 33 | 34 | if __name__ == "__main__": 35 | 36 | part1() 37 | part2() 38 | -------------------------------------------------------------------------------- /2015/day02/code.py: -------------------------------------------------------------------------------- 1 | import time,os 2 | 3 | def profiler(method): 4 | def wrapper_method(*arg, **kw): 5 | t = time.time() 6 | method(*arg, **kw) 7 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 8 | return wrapper_method 9 | 10 | @profiler 11 | def part1(): 12 | 13 | with open('input.txt', 'r') as f_in : 14 | area = 0 15 | for l in f_in: 16 | ls = list(map(int,l.strip().split('x'))) 17 | ls.sort() 18 | area += 3*ls[0]*ls[1] + 2*ls[0]*ls[2] + 2*ls[1]*ls[2] 19 | 20 | print(area) 21 | 22 | @profiler 23 | def part2(): 24 | with open('input.txt', 'r') as f_in : 25 | ribbon = 0 26 | for l in f_in: 27 | ls = list(map(int,l.strip().split('x'))) 28 | ls.sort() 29 | ribbon += 2*ls[0] + 2*ls[1] 30 | ribbon += ls[0] * ls[1] * ls[2] 31 | 32 | print(ribbon) 33 | 34 | 35 | if __name__ == "__main__": 36 | 37 | part1() 38 | part2() 39 | -------------------------------------------------------------------------------- /2015/day03/code.py: -------------------------------------------------------------------------------- 1 | import time,os 2 | from collections import defaultdict 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | method(*arg, **kw) 8 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 9 | return wrapper_method 10 | 11 | @profiler 12 | def part1(): 13 | 14 | moves = {'^' : 1j , 'v' : -1j , '<' : -1 , '>' : 1} 15 | with open('input.txt', 'r') as f_in : 16 | l = f_in.read().strip() 17 | pt = 0 + 0j 18 | houses = defaultdict(int) 19 | houses[pt] = 1 20 | for d in l: 21 | pt += moves[d] 22 | houses[pt] += 1 23 | 24 | print(len(houses)) 25 | 26 | @profiler 27 | def part2(): 28 | moves = {'^' : 1j , 'v' : -1j , '<' : -1 , '>' : 1} 29 | with open('input.txt', 'r') as f_in : 30 | l = f_in.read().strip() 31 | pt_s = 0 + 0j 32 | pt_r = pt_s 33 | houses = defaultdict(int) 34 | houses[pt_s] = 1 35 | for d in range(len(l) // 2): 36 | pt_s += moves[l[2*d]] 37 | pt_r += moves[l[2*d+1]] 38 | 39 | houses[pt_s] += 1 40 | houses[pt_r] += 1 41 | 42 | print(len(houses)) 43 | 44 | 45 | if __name__ == "__main__": 46 | 47 | part1() 48 | part2() 49 | -------------------------------------------------------------------------------- /2015/day04/code.py: -------------------------------------------------------------------------------- 1 | import time,os 2 | from collections import defaultdict 3 | import hashlib 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | method(*arg, **kw) 9 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 10 | return wrapper_method 11 | 12 | @profiler 13 | def part1(): 14 | 15 | with open('input.txt', 'r') as f_in : 16 | l = f_in.read().strip() 17 | val = 0 18 | while True: 19 | st = 'yzbqklnj' + str(val) 20 | hash = hashlib.md5(bytes(st,'utf-8')).hexdigest() 21 | if hash[0] == hash[1] == hash[2] == hash[3] == hash[4] == '0': 22 | print(val) 23 | break 24 | val += 1 25 | 26 | 27 | @profiler 28 | def part2(): 29 | 30 | with open('input.txt', 'r') as f_in : 31 | l = f_in.read().strip() 32 | val = 0 33 | while True: 34 | st = 'yzbqklnj' + str(val) 35 | hash = hashlib.md5(bytes(st,'utf-8')).hexdigest() 36 | if hash[0] == hash[1] == hash[2] == hash[3] == hash[4] == hash[5] == '0': 37 | print(val) 38 | break 39 | val += 1 40 | 41 | 42 | 43 | if __name__ == "__main__": 44 | 45 | part1() 46 | part2() 47 | -------------------------------------------------------------------------------- /2015/day05/code.py: -------------------------------------------------------------------------------- 1 | import time,os,re 2 | 3 | def profiler(method): 4 | def wrapper_method(*arg, **kw): 5 | t = time.time() 6 | method(*arg, **kw) 7 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 8 | return wrapper_method 9 | 10 | 11 | def is_nice(l): 12 | has_vowels = len(re.findall(r'[aeiou]', l)) > 2 13 | has_repeated = any([l[i] == l[i+1] for i in range(len(l)-1)]) 14 | has_bad = 'ab' in l or 'cd' in l or 'pq' in l or 'xy' in l 15 | return has_vowels and has_repeated and not has_bad 16 | 17 | def is_nice_2(l): 18 | has_repeated = re.match(r'.*(\w\w).*\1.*' , l) is not None 19 | has_chars = re.match(r'.*(\w)\w\1.*' , l) is not None 20 | return has_repeated and has_chars 21 | 22 | @profiler 23 | def part1(): 24 | with open('input.txt', 'r') as f: 25 | print(sum([*map(is_nice,f.read().split('\n'))])) 26 | 27 | 28 | @profiler 29 | def part2(): 30 | with open('input.txt', 'r') as f: 31 | print(sum([*map(is_nice_2,f.read().split('\n'))])) 32 | 33 | 34 | if __name__ == "__main__": 35 | 36 | part1() 37 | part2() 38 | -------------------------------------------------------------------------------- /2015/day06/code.py: -------------------------------------------------------------------------------- 1 | import time,os,re 2 | 3 | def profiler(method): 4 | def wrapper_method(*arg, **kw): 5 | t = time.time() 6 | method(*arg, **kw) 7 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 8 | return wrapper_method 9 | 10 | 11 | @profiler 12 | def part1(): 13 | grid = [ [False for _ in range(1000)] for _ in range(1000)] 14 | with open('input.txt', 'r') as f: 15 | for l in f: 16 | l = l.strip() 17 | d = [*map(int , list(re.findall(r'\d+' , l)))] 18 | for x in range(d[0] , d[2] + 1): 19 | for y in range(d[1] , d[3] + 1): 20 | if 'toggle' in l: 21 | grid[x][y] = not grid[x][y] 22 | elif 'on' in l: 23 | grid[x][y] = True 24 | elif 'off' in l: 25 | grid[x][y] = False 26 | 27 | print(sum([sum(l) for l in grid])) 28 | 29 | 30 | @profiler 31 | def part2(): 32 | grid = [ [0 for _ in range(1000)] for _ in range(1000)] 33 | with open('input.txt', 'r') as f: 34 | for l in f: 35 | l = l.strip() 36 | d = [*map(int , list(re.findall(r'\d+' , l)))] 37 | for x in range(d[0] , d[2] + 1): 38 | for y in range(d[1] , d[3] + 1): 39 | if 'toggle' in l: 40 | grid[x][y] += 2 41 | elif 'on' in l: 42 | grid[x][y] += 1 43 | elif 'off' in l: 44 | grid[x][y] = max(grid[x][y] - 1 ,0) 45 | 46 | print(sum([sum(l) for l in grid])) 47 | 48 | 49 | if __name__ == "__main__": 50 | 51 | part1() 52 | part2() 53 | -------------------------------------------------------------------------------- /2015/day08/code.py: -------------------------------------------------------------------------------- 1 | import time,os,re 2 | from collections import defaultdict 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 9 | return ret 10 | return wrapper_method 11 | 12 | @profiler 13 | def part1(): 14 | with open('input.txt', 'r') as f: 15 | print(sum([len(l.strip()) - len(eval(l.strip())) for l in f ])) 16 | 17 | @profiler 18 | def part2(): 19 | with open('input.txt', 'r') as f: 20 | print(sum([2 + l.count('\\') + l.count(r'"') for l in f])) 21 | 22 | if __name__ == "__main__": 23 | 24 | part1() 25 | part2() 26 | -------------------------------------------------------------------------------- /2015/day09/code.py: -------------------------------------------------------------------------------- 1 | import time,os,re 2 | from collections import defaultdict 3 | from itertools import permutations 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | ret = method(*arg, **kw) 9 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | @profiler 14 | def part1(): 15 | with open('input.txt', 'r') as f: 16 | dsts = {} 17 | places = set() 18 | for l in f: 19 | l = l.strip() 20 | p = l.split(' = ') 21 | t = p[0].split(' to ') 22 | t.sort() 23 | places.update(t) 24 | dsts[tuple(t)] = int(p[1]) 25 | 26 | min_dist = 1000000 27 | 28 | for rt in permutations(places): 29 | dst = 0 30 | for i in range(len(rt) - 1): 31 | t = [rt[i] , rt[i+1] ] 32 | t.sort() 33 | dst += dsts[tuple(t)] 34 | 35 | if dst < min_dist : min_dist = dst 36 | 37 | print(min_dist) 38 | 39 | @profiler 40 | def part2(): 41 | with open('input.txt', 'r') as f: 42 | dsts = {} 43 | places = set() 44 | for l in f: 45 | l = l.strip() 46 | p = l.split(' = ') 47 | t = p[0].split(' to ') 48 | t.sort() 49 | places.update(t) 50 | dsts[tuple(t)] = int(p[1]) 51 | 52 | max_dist = 0 53 | 54 | for rt in permutations(places): 55 | dst = 0 56 | for i in range(len(rt) - 1): 57 | t = [rt[i] , rt[i+1] ] 58 | t.sort() 59 | dst += dsts[tuple(t)] 60 | 61 | if dst > max_dist : max_dist = dst 62 | 63 | print(max_dist) 64 | 65 | if __name__ == "__main__": 66 | 67 | part1() 68 | part2() 69 | -------------------------------------------------------------------------------- /2015/day10/code.py: -------------------------------------------------------------------------------- 1 | import time,re 2 | 3 | def profiler(method): 4 | def wrapper_method(*arg, **kw): 5 | t = time.time() 6 | ret = method(*arg, **kw) 7 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 8 | return ret 9 | return wrapper_method 10 | 11 | 12 | def replace(match_obj): 13 | s = match_obj.group(1) 14 | return str(len(s)) + s[0] 15 | 16 | @profiler 17 | def part1(): 18 | 19 | pswd = '3113322113' 20 | 21 | for _ in range(40): 22 | val = re.sub(r'((\d)\2*)',replace,val) 23 | 24 | print(len(val)) 25 | 26 | 27 | @profiler 28 | def part2(): 29 | val = '3113322113' 30 | 31 | for _ in range(50): 32 | val = re.sub(r'((\d)\2*)',replace,val) 33 | 34 | print(len(val)) 35 | 36 | 37 | if __name__ == "__main__": 38 | 39 | part1() 40 | part2() 41 | -------------------------------------------------------------------------------- /2015/day11/code.py: -------------------------------------------------------------------------------- 1 | import time,re 2 | 3 | def profiler(method): 4 | def wrapper_method(*arg, **kw): 5 | t = time.time() 6 | ret = method(*arg, **kw) 7 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 8 | return ret 9 | return wrapper_method 10 | 11 | 12 | def next_pass(s): 13 | idx = 1 14 | s = list(s) 15 | while True: 16 | ch = s[-idx] 17 | if ch == 'z': 18 | s[-idx] = 'a' 19 | idx += 1 20 | else : 21 | s[-idx] = chr(ord(ch) + 1) 22 | break 23 | 24 | return ''.join(s) 25 | 26 | def is_valid(pswd): 27 | invalid_char = 'i' in pswd or 'o' in pswd or 'l' in pswd 28 | three_seq = any([ ord(pswd[i-1]) + 1 == ord(pswd[i]) == ord(pswd[i+1]) - 1 for i in range(1,len(pswd) -1)]) 29 | has_2_pair = re.match(r'.*(\w)\1.*([^\1])\2.*',pswd) is not None 30 | 31 | return not invalid_char and three_seq and has_2_pair 32 | 33 | @profiler 34 | def part1(): 35 | 36 | pswd = 'hxbxwxba' 37 | while True: 38 | if is_valid(pswd): 39 | break 40 | pswd = next_pass(pswd) 41 | 42 | print(pswd) 43 | 44 | @profiler 45 | def part2(): 46 | 47 | pswd = 'hxbxwxba' 48 | while True: 49 | if is_valid(pswd): 50 | break 51 | pswd = next_pass(pswd) 52 | 53 | pswd = next_pass(pswd) 54 | 55 | while True: 56 | if is_valid(pswd): 57 | break 58 | pswd = next_pass(pswd) 59 | 60 | print(pswd) 61 | 62 | 63 | 64 | if __name__ == "__main__": 65 | 66 | part1() 67 | part2() 68 | -------------------------------------------------------------------------------- /2015/day12/code.py: -------------------------------------------------------------------------------- 1 | import time,re 2 | import json 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 9 | return ret 10 | return wrapper_method 11 | 12 | @profiler 13 | def part1(): 14 | 15 | with open('input.txt') as f: 16 | data = f.read() 17 | 18 | nums = list(map(int,re.findall(r'-?\d+' , data))) 19 | print(sum(nums)) 20 | 21 | 22 | 23 | def sum_recursive(data): 24 | if isinstance(data,int): 25 | return data 26 | elif isinstance(data,list): 27 | return sum([sum_recursive(d) for d in data]) 28 | elif isinstance(data,str): 29 | return 0 30 | elif isinstance(data,dict): 31 | if 'red' in data.values(): 32 | return 0 33 | else : 34 | return sum([sum_recursive(data[d]) for d in data]) 35 | 36 | @profiler 37 | def part2(): 38 | 39 | with open('input.txt') as f: 40 | data = json.load(f) 41 | 42 | print(sum_recursive(data)) 43 | 44 | if __name__ == "__main__": 45 | 46 | part1() 47 | part2() 48 | -------------------------------------------------------------------------------- /2015/day13/code.py: -------------------------------------------------------------------------------- 1 | import time,re 2 | from collections import defaultdict 3 | from itertools import permutations 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | ret = method(*arg, **kw) 9 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | @profiler 14 | def part1(): 15 | 16 | heat = defaultdict(dict) 17 | ppl = set() 18 | with open('input.txt') as f: 19 | for l in f: 20 | s = 1 21 | p = l.strip().split() 22 | ppl.add(p[0]) 23 | if 'lose' in l : s = -1 24 | heat[p[0]][p[-1][:-1]] = s * int(p[3]) 25 | 26 | happ = 0 27 | for s in permutations(ppl): 28 | tmp = sum([ heat[s[i]][s[i-1]] + heat[s[i]][s[i+1]] for i in range(1,len(s)-1)]) 29 | tmp += heat[s[0]][s[1]] + heat[s[0]][s[-1]] 30 | tmp += heat[s[-1]][s[0]] + heat[s[-1]][s[-2]] 31 | 32 | if tmp > happ : happ = tmp 33 | print(happ) 34 | 35 | 36 | @profiler 37 | def part2(): 38 | 39 | heat = defaultdict(dict) 40 | ppl = set() 41 | with open('input.txt') as f: 42 | for l in f: 43 | s = 1 44 | p = l.strip().split() 45 | ppl.add(p[0]) 46 | if 'lose' in l : s = -1 47 | heat[p[0]][p[-1][:-1]] = s * int(p[3]) 48 | 49 | for d in ppl: 50 | heat[d]['me'] = 0 51 | 52 | ppl.add('me') 53 | heat['me'] = defaultdict(int) 54 | 55 | happ = 0 56 | for s in permutations(ppl): 57 | tmp = sum([ heat[s[i]][s[i-1]] + heat[s[i]][s[i+1]] for i in range(1,len(s)-1)]) 58 | tmp += heat[s[0]][s[1]] + heat[s[0]][s[-1]] 59 | tmp += heat[s[-1]][s[0]] + heat[s[-1]][s[-2]] 60 | 61 | if tmp > happ : happ = tmp 62 | 63 | print(happ) 64 | 65 | if __name__ == "__main__": 66 | 67 | part1() 68 | part2() 69 | -------------------------------------------------------------------------------- /2015/day14/code.py: -------------------------------------------------------------------------------- 1 | import time,re 2 | from collections import defaultdict 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 9 | return ret 10 | return wrapper_method 11 | 12 | @profiler 13 | def part1(): 14 | 15 | deers = {} 16 | t = 2503 17 | with open('input.txt') as f: 18 | for l in f: 19 | p = l.strip().split() 20 | deers[p[0]] = (int(p[3]) , int(p[6]) , int(p[13])) 21 | 22 | race = {} 23 | for d in deers: 24 | p = deers[d] 25 | cycle = p[1] + p[2] 26 | dst = (t // cycle) * p[0] * p[1] 27 | if t%cycle > p[1]: 28 | dst += p[0] * p[1] 29 | else : 30 | dst += t%cycle * p[0] 31 | 32 | race[d] = dst 33 | 34 | print(max(race.values())) 35 | 36 | @profiler 37 | def part2(): 38 | 39 | deers = {} 40 | t0 = 2503 41 | with open('input.txt') as f: 42 | for l in f: 43 | p = l.strip().split() 44 | deers[p[0]] = (int(p[3]) , int(p[6]) , int(p[13])) 45 | 46 | race_acc = defaultdict(int) 47 | 48 | for t in range(1,t0+1): 49 | 50 | race = {} 51 | 52 | for d in deers: 53 | p = deers[d] 54 | cycle = p[1] + p[2] 55 | dst = (t // cycle) * p[0] * p[1] 56 | if t%cycle > p[1]: 57 | dst += p[0] * p[1] 58 | else : 59 | dst += t%cycle * p[0] 60 | 61 | race[d] = dst 62 | 63 | m = max(race.values()) 64 | 65 | for d in deers: 66 | if race[d] == m: 67 | race_acc[d] += 1 68 | 69 | print(max(race_acc.values())) 70 | 71 | if __name__ == "__main__": 72 | 73 | part1() 74 | part2() 75 | -------------------------------------------------------------------------------- /2015/day17/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import re 3 | from itertools import combinations 4 | from collections import defaultdict 5 | 6 | 7 | def profiler(method): 8 | def wrapper_method(*arg, **kw): 9 | t = time.time() 10 | ret = method(*arg, **kw) 11 | print('Method ' + method.__name__ + ' took : ' + 12 | "{:2.5f}".format(time.time()-t) + ' sec') 13 | return ret 14 | return wrapper_method 15 | 16 | 17 | @profiler 18 | def part1(): 19 | 20 | with open('input.txt') as f: 21 | inp = [*map(int, f.read().split())] 22 | 23 | cnt = 0 24 | for i in range(len(inp)): 25 | for c in combinations(inp, i+1): 26 | if sum(c) == 150: 27 | cnt += 1 28 | 29 | print(cnt) 30 | 31 | 32 | @profiler 33 | def part2(): 34 | 35 | with open('input.txt') as f: 36 | inp = [*map(int, f.read().split())] 37 | 38 | cnt = defaultdict(int) 39 | 40 | for i in range(len(inp)): 41 | for c in combinations(inp, i+1): 42 | if sum(c) == 150: 43 | cnt[i+1] += 1 44 | 45 | if len(cnt) > 1: 46 | break 47 | 48 | print(cnt[min(cnt.keys())]) 49 | 50 | 51 | if __name__ == "__main__": 52 | 53 | part1() 54 | part2() 55 | -------------------------------------------------------------------------------- /2015/day19/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import re 3 | from collections import defaultdict,deque 4 | 5 | 6 | def profiler(method): 7 | def wrapper_method(*arg, **kw): 8 | t = time.time() 9 | ret = method(*arg, **kw) 10 | print('Method ' + method.__name__ + ' took : ' + 11 | "{:2.5f}".format(time.time()-t) + ' sec') 12 | return ret 13 | return wrapper_method 14 | 15 | 16 | def replacenth(string, sub, wanted, n): 17 | where = [m.start() for m in re.finditer(sub, string)][n-1] 18 | before = string[:where] 19 | after = string[where:] 20 | after = after.replace(sub, wanted, 1) 21 | newString = before + after 22 | return newString 23 | 24 | 25 | @profiler 26 | def part1(): 27 | 28 | with open('input.txt') as f: 29 | ls, m = f.read().split('\n\n') 30 | 31 | m = m.strip() 32 | tra = defaultdict(list) 33 | for l in ls.split('\n'): 34 | p = l.strip().split(' => ') 35 | tra[p[0]].append(p[1]) 36 | 37 | comb = set() 38 | 39 | for d in tra: 40 | for n in tra[d]: 41 | for i in range(m.count(d)): 42 | comb.add(replacenth(m, d, n, i+1)) 43 | 44 | print(len(comb)) 45 | 46 | 47 | @profiler 48 | def part2(): 49 | 50 | with open('input.txt') as f: 51 | ls, m = f.read().split('\n\n') 52 | 53 | m = m.strip() 54 | tra = {} 55 | for l in ls.split('\n'): 56 | p = l.strip().split(' => ') 57 | tra[p[1]] = p[0] 58 | 59 | cnt = 0 60 | 61 | while m != 'e': 62 | for e in tra: 63 | cnt += m.count(e) 64 | m = m.replace(e,tra[e]) 65 | 66 | print(cnt) 67 | 68 | if __name__ == "__main__": 69 | 70 | part1() 71 | part2() 72 | 73 | -------------------------------------------------------------------------------- /2015/day20/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import re 3 | from collections import defaultdict 4 | from functools import reduce 5 | 6 | 7 | def profiler(method): 8 | def wrapper_method(*arg, **kw): 9 | t = time.time() 10 | ret = method(*arg, **kw) 11 | print('Method ' + method.__name__ + ' took : ' + 12 | "{:2.5f}".format(time.time()-t) + ' sec') 13 | return ret 14 | return wrapper_method 15 | 16 | 17 | def fac(n): 18 | return set(reduce(list.__add__, 19 | ([i, int(n//i)] for i in range(1, int(n**0.5) + 1) if n % i == 0))) 20 | 21 | 22 | @profiler 23 | def part1(): 24 | 25 | inp = 36000000 26 | 27 | for i in range(100000,1000000): 28 | if sum(fac(i)) * 10 >= inp : 29 | print(i) 30 | break 31 | 32 | 33 | @profiler 34 | def part2(): 35 | 36 | inp = 36000000 37 | 38 | for i in range(100000,1000000): 39 | l = list(fac(i)) 40 | l.sort() 41 | if sum(e for e in l if i//e < 50) * 11 >= inp: 42 | print(i) 43 | break 44 | 45 | if __name__ == "__main__": 46 | 47 | part1() 48 | part2() 49 | 50 | -------------------------------------------------------------------------------- /2015/day24/code.py: -------------------------------------------------------------------------------- 1 | import random 2 | import time 3 | import re 4 | from itertools import combinations 5 | from operator import mul 6 | from functools import reduce 7 | 8 | 9 | def profiler(method): 10 | def wrapper_method(*arg, **kw): 11 | t = time.time() 12 | ret = method(*arg, **kw) 13 | print('Method ' + method.__name__ + ' took : ' + 14 | "{:2.5f}".format(time.time()-t) + ' sec') 15 | return ret 16 | return wrapper_method 17 | 18 | 19 | @profiler 20 | def part1(): 21 | 22 | vals = [int(l) for l in open('input.txt').read().split('\n')] 23 | w = sum(vals)//3 24 | grps = [] 25 | for i in range(1, len(vals)): 26 | grps += [reduce(mul, grp) 27 | for grp in combinations(vals, i) if sum(grp) == w] 28 | 29 | print(min(grps)) 30 | 31 | 32 | @profiler 33 | def part2(): 34 | 35 | vals = [int(l) for l in open('input.txt').read().split('\n')] 36 | w = sum(vals)//4 37 | grps = [] 38 | for i in range(1, len(vals)): 39 | grps += [reduce(mul, grp) 40 | for grp in combinations(vals, i) if sum(grp) == w] 41 | 42 | print(min(grps)) 43 | 44 | 45 | if __name__ == "__main__": 46 | 47 | part1() 48 | part2() 49 | -------------------------------------------------------------------------------- /2015/day25/code.py: -------------------------------------------------------------------------------- 1 | import random 2 | import time 3 | import re 4 | from itertools import combinations 5 | from operator import mul 6 | from functools import reduce 7 | 8 | 9 | def profiler(method): 10 | def wrapper_method(*arg, **kw): 11 | t = time.time() 12 | ret = method(*arg, **kw) 13 | print('Method ' + method.__name__ + ' took : ' + 14 | "{:2.5f}".format(time.time()-t) + ' sec') 15 | return ret 16 | return wrapper_method 17 | 18 | 19 | @profiler 20 | def part1(): 21 | 22 | a1 = 20151125 23 | fac = 252533 24 | div = 33554393 25 | # input 26 | row = 2981 27 | column = 3075 28 | 29 | n = (row + column - 1)*(row + column - 2)//2 + column -1 30 | print((a1* pow(fac,n,div))%div) 31 | 32 | 33 | if __name__ == "__main__": 34 | 35 | part1() 36 | -------------------------------------------------------------------------------- /2016/day01/code.py: -------------------------------------------------------------------------------- 1 | import time,os 2 | 3 | def profiler(method): 4 | def wrapper_method(*arg, **kw): 5 | t = time.time() 6 | method(*arg, **kw) 7 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 8 | return wrapper_method 9 | 10 | @profiler 11 | def part1(): 12 | 13 | pos = 0 + 0j 14 | dr = 0 + 1j 15 | 16 | with open('input.txt', 'r') as f_in : 17 | ls = f_in.read().strip().split(', ') 18 | 19 | for m in ls: 20 | if 'R' in m: 21 | dr *= -1j 22 | else : 23 | dr *= 1j 24 | 25 | pos += dr*int(m[1:]) 26 | 27 | print(abs(pos.real) + abs(pos.imag)) 28 | 29 | @profiler 30 | def part2(): 31 | 32 | visited = set() 33 | pos = 0 + 0j 34 | dr = 0 + 1j 35 | 36 | with open('input.txt', 'r') as f_in : 37 | ls = f_in.read().strip().split(', ') 38 | 39 | for m in ls: 40 | if 'R' in m: 41 | dr *= -1j 42 | else : 43 | dr *= +1j 44 | 45 | for _ in range(int(m[1:])): 46 | pos += dr 47 | 48 | if pos not in visited: 49 | visited.add(pos) 50 | else : 51 | print(abs(pos.real) + abs(pos.imag)) 52 | return 53 | 54 | if __name__ == "__main__": 55 | 56 | part1() 57 | part2() 58 | -------------------------------------------------------------------------------- /2016/day03/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import os 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | method(*arg, **kw) 9 | print('Method ' + method.__name__ + ' took : ' + 10 | "{:2.5f}".format(time.time()-t) + ' sec') 11 | return wrapper_method 12 | 13 | 14 | def is_triangle(a, b, c): 15 | return a + b > c and a + c > b and b + c > a 16 | 17 | 18 | @profiler 19 | def part1(): 20 | 21 | with open('input.txt') as f_in: 22 | ls = [list(map(int, l.split())) 23 | for l in f_in.read().strip().split('\n')] 24 | 25 | cnt = 0 26 | for l in ls: 27 | if is_triangle(l[0], l[1], l[2]): 28 | cnt += 1 29 | 30 | print(cnt) 31 | 32 | 33 | @profiler 34 | def part2(): 35 | 36 | with open('input.txt') as f_in: 37 | ls = [list(map(int, l.split())) 38 | for l in f_in.read().strip().split('\n')] 39 | 40 | cnt = 0 41 | for c in range(3): 42 | new_l = [t[c] for t in ls] 43 | 44 | for i in range(0, len(new_l), 3): 45 | if is_triangle(new_l[i], new_l[i+1], new_l[i+2]): 46 | cnt += 1 47 | 48 | print(cnt) 49 | 50 | 51 | if __name__ == "__main__": 52 | 53 | part1() 54 | part2() 55 | -------------------------------------------------------------------------------- /2016/day05/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import os 3 | import hashlib 4 | from collections import Counter 5 | 6 | 7 | def profiler(method): 8 | def wrapper_method(*arg, **kw): 9 | t = time.time() 10 | method(*arg, **kw) 11 | print('Method ' + method.__name__ + ' took : ' + 12 | "{:2.5f}".format(time.time()-t) + ' sec') 13 | return wrapper_method 14 | 15 | 16 | @profiler 17 | def part1(): 18 | 19 | inp = 'abbhdwsy' 20 | 21 | code = [] 22 | inc = 1 23 | 24 | while len(code) < 8: 25 | tmp = inp + str(inc) 26 | hash = hashlib.md5(bytes(tmp, 'utf-8')).hexdigest() 27 | if hash[0] == hash[1] == hash[2] == hash[3] == hash[4] == '0': 28 | code.append(hash[5]) 29 | 30 | inc += 1 31 | 32 | print(''.join(code)) 33 | 34 | @profiler 35 | def part2(): 36 | 37 | inp = 'abbhdwsy' 38 | 39 | code = ['-'] * 8 40 | inc = 1 41 | 42 | while code.count('-') > 0: 43 | tmp = inp + str(inc) 44 | hash = hashlib.md5(bytes(tmp, 'utf-8')).hexdigest() 45 | if hash[0] == hash[1] == hash[2] == hash[3] == hash[4] == '0': 46 | if int(hash[5],16) < 8: 47 | if code[int(hash[5],16)] == '-': 48 | code[int(hash[5],16)] = hash[6] 49 | 50 | inc += 1 51 | 52 | print(''.join(code)) 53 | 54 | 55 | if __name__ == "__main__": 56 | 57 | part1() 58 | part2() 59 | -------------------------------------------------------------------------------- /2016/day06/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import os 3 | from collections import Counter 4 | 5 | 6 | def profiler(method): 7 | def wrapper_method(*arg, **kw): 8 | t = time.time() 9 | method(*arg, **kw) 10 | print('Method ' + method.__name__ + ' took : ' + 11 | "{:2.5f}".format(time.time()-t) + ' sec') 12 | return wrapper_method 13 | 14 | 15 | @profiler 16 | def part1(): 17 | 18 | with open('input.txt') as f: 19 | inp = f.read().split('\n') 20 | 21 | table = [] 22 | for i in range(len(inp[0])): 23 | t = Counter([l[i] for l in inp]) 24 | table.append(t.most_common()[0][0]) 25 | 26 | print(''.join(table)) 27 | 28 | 29 | @profiler 30 | def part2(): 31 | 32 | with open('input.txt') as f: 33 | inp = f.read().split('\n') 34 | 35 | table = [] 36 | for i in range(len(inp[0])): 37 | t = Counter([l[i] for l in inp]) 38 | table.append(t.most_common()[-1][0]) 39 | 40 | print(''.join(table)) 41 | 42 | 43 | if __name__ == "__main__": 44 | 45 | part1() 46 | part2() 47 | -------------------------------------------------------------------------------- /2016/day08/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import os 3 | import re 4 | 5 | 6 | def profiler(method): 7 | def wrapper_method(*arg, **kw): 8 | t = time.time() 9 | method(*arg, **kw) 10 | print('Method ' + method.__name__ + ' took : ' + 11 | "{:2.5f}".format(time.time()-t) + ' sec') 12 | return wrapper_method 13 | 14 | 15 | def print_grid(grid): 16 | for y in range(6): 17 | for x in range(50): 18 | ch = '#' if (x, y) in grid else ' ' 19 | print(ch, end='') 20 | print() 21 | 22 | 23 | @profiler 24 | def part1(): 25 | cnt = 0 26 | for l in open('input.txt').read().split('\n'): 27 | if 'rect' in l: 28 | cnt += eval(l.split()[1].replace('x', '*')) 29 | 30 | print(cnt) 31 | 32 | 33 | @profiler 34 | def part2(): 35 | 36 | grid = set() 37 | 38 | for l in open('input.txt').read().split('\n'): 39 | if 'rect' in l: 40 | dim = list(map(int, l.split()[1].split('x'))) 41 | for x in range(dim[0]): 42 | for y in range(dim[1]): 43 | grid.add((x, y)) 44 | 45 | elif 'row' in l: 46 | rot = list(map(int, re.findall(r'\d+', l))) 47 | tmp = set() 48 | for p in grid: 49 | if p[1] != rot[0]: 50 | tmp.add(p) 51 | else: 52 | tmp.add(((p[0] + rot[1]) % 50, rot[0])) 53 | grid = tmp 54 | 55 | elif 'column' in l: 56 | rot = list(map(int, re.findall(r'\d+', l))) 57 | tmp = set() 58 | for p in grid: 59 | if p[0] != rot[0]: 60 | tmp.add(p) 61 | else: 62 | tmp.add((p[0], (p[1]+rot[1]) % 6)) 63 | grid = tmp 64 | 65 | print_grid(grid) 66 | 67 | 68 | if __name__ == "__main__": 69 | 70 | # part1() 71 | part2() 72 | -------------------------------------------------------------------------------- /2016/day09/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import os 3 | import re 4 | 5 | 6 | def profiler(method): 7 | def wrapper_method(*arg, **kw): 8 | t = time.time() 9 | ret = method(*arg, **kw) 10 | print('Method ' + method.__name__ + ' took : ' + 11 | "{:2.5f}".format(time.time()-t) + ' sec') 12 | return ret 13 | return wrapper_method 14 | 15 | 16 | @profiler 17 | def part1(): 18 | st = open('input.txt').read().strip() 19 | 20 | while '(' in st: 21 | p = re.findall(r'\(\d+x\d+\)', st) 22 | p_pos = st.find(p[0]) 23 | l, rep = list(map(int, p[0][1:-1].split('x'))) 24 | new_st = st[p_pos+len(p[0]):p_pos+l+len(p[0]) 25 | ].replace('(', '[').replace(')', ']') 26 | st = st.replace(st[p_pos:p_pos+l+len(p[0])], new_st * rep) 27 | 28 | print(len(st)) 29 | 30 | 31 | def get_size(st): 32 | 33 | if '(' not in st: 34 | return len(st) 35 | p = re.findall(r'\(\d+x\d+\)', st) 36 | p_pos = st.find(p[0]) 37 | l, rep = list(map(int, p[0][1:-1].split('x'))) 38 | return len(st[:p_pos]) + get_size(st[p_pos+len(p[0]):p_pos+len(p[0])+l]) * rep + get_size(st[p_pos+len(p[0])+l:]) 39 | 40 | 41 | @profiler 42 | def part2(): 43 | print(get_size(open('input.txt').read().strip())) 44 | 45 | 46 | if __name__ == "__main__": 47 | 48 | part1() 49 | part2() 50 | -------------------------------------------------------------------------------- /2016/day11/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import re 3 | from collections import defaultdict 4 | 5 | 6 | def profiler(method): 7 | def wrapper_method(*arg, **kw): 8 | t = time.time() 9 | ret = method(*arg, **kw) 10 | print('Method ' + method.__name__ + ' took : ' + 11 | "{:2.5f}".format(time.time()-t) + ' sec') 12 | return ret 13 | return wrapper_method 14 | 15 | 16 | @profiler 17 | def part1(): 18 | 19 | plan = [] 20 | 21 | for l in open('input.txt').read().split('\n'): 22 | plan.append(l.count(',')+1) 23 | 24 | print(sum(2 * sum(plan[:f]) - 3 for f in range(1, 4))) 25 | 26 | 27 | @profiler 28 | def part2(): 29 | 30 | plan = [] 31 | 32 | for l in open('input.txt').read().split('\n'): 33 | plan.append(l.count(',')+1) 34 | 35 | plan[0] += 4 36 | 37 | print(sum(2 * sum(plan[:f]) - 3 for f in range(1, 4))) 38 | 39 | 40 | if __name__ == "__main__": 41 | 42 | part1() 43 | part2() 44 | -------------------------------------------------------------------------------- /2016/day15/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | 3 | def profiler(method): 4 | def wrapper_method(*arg, **kw): 5 | t = time.time() 6 | ret = method(*arg, **kw) 7 | print('Method ' + method.__name__ + ' took : ' + 8 | "{:2.5f}".format(time.time()-t) + ' sec') 9 | return ret 10 | return wrapper_method 11 | 12 | 13 | def get_nums(l): 14 | ps = l.strip().split() 15 | return (int(ps[3]), int(ps[-1][:-1])) 16 | 17 | 18 | @profiler 19 | def part_1(): 20 | with open('day15/input.txt') as f: 21 | inp = [get_nums(l) for l in f.readlines()] 22 | 23 | itter = 0 24 | while not all((itter + i + disc[1]) % disc[0] == 0 for i, disc in enumerate(inp)): 25 | itter += 1 26 | 27 | print(itter-1) 28 | 29 | @profiler 30 | def part_2(): 31 | with open('day15/input.txt') as f: 32 | inp = [get_nums(l) for l in f.readlines()] 33 | inp.append((11, 0)) 34 | 35 | itter = 0 36 | while not all((itter + i + disc[1]) % disc[0] == 0 for i, disc in enumerate(inp)): 37 | itter += 1 38 | 39 | print(itter-1) 40 | 41 | if __name__ == "__main__": 42 | 43 | part_1() 44 | part_2() 45 | -------------------------------------------------------------------------------- /2016/day16/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import re 3 | import hashlib 4 | import sys 5 | 6 | 7 | def profiler(method): 8 | def wrapper_method(*arg, **kw): 9 | t = time.time() 10 | ret = method(*arg, **kw) 11 | print('Method ' + method.__name__ + ' took : ' + 12 | "{:2.5f}".format(time.time()-t) + ' sec') 13 | return ret 14 | return wrapper_method 15 | 16 | 17 | @profiler 18 | def part1(): 19 | inp = '00111101111101000' 20 | trg_len = 272 21 | 22 | while len(inp) < trg_len: 23 | b = inp[::-1] 24 | b = b.replace('0', 'x').replace('1', '0').replace('x', '1') 25 | inp = inp + '0' + b 26 | 27 | inp = inp[:trg_len] 28 | 29 | check_sum = '' 30 | 31 | while len(check_sum) % 2 == 0: 32 | if check_sum == '': 33 | check_sum = inp 34 | 35 | tmp = [] 36 | for i in range(0,len(check_sum),2): 37 | tmp.append('1' if check_sum[i] == check_sum[i+1] else '0') 38 | 39 | check_sum = ''.join(tmp) 40 | 41 | print(check_sum) 42 | 43 | 44 | @profiler 45 | def part2(): 46 | inp = '00111101111101000' 47 | trg_len = 35651584 48 | 49 | 50 | while len(inp) < trg_len: 51 | b = inp[::-1] 52 | b = b.replace('0', 'x').replace('1', '0').replace('x', '1') 53 | inp = inp + '0' + b 54 | 55 | inp = inp[:trg_len] 56 | 57 | check_sum = '' 58 | 59 | while len(check_sum) % 2 == 0: 60 | if check_sum == '': 61 | check_sum = inp 62 | 63 | tmp = [] 64 | for i in range(0,len(check_sum),2): 65 | tmp.append('1' if check_sum[i] == check_sum[i+1] else '0') 66 | 67 | check_sum = ''.join(tmp) 68 | 69 | print(check_sum) 70 | 71 | 72 | if __name__ == "__main__": 73 | 74 | part1() 75 | part2() 76 | -------------------------------------------------------------------------------- /2016/day19/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | from collections import deque 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | ret = method(*arg, **kw) 9 | print('Method ' + method.__name__ + ' took : ' + 10 | "{:2.5f}".format(time.time()-t) + ' sec') 11 | return ret 12 | return wrapper_method 13 | 14 | 15 | def josephus(n, k): 16 | r = 0 17 | for i in range(1, n+1): 18 | r = (r+k) % i 19 | return r 20 | 21 | 22 | @profiler 23 | def part1(): 24 | 25 | inp = 3017957 26 | 27 | print(josephus(inp, 2)) 28 | 29 | 30 | @profiler 31 | def part2(): 32 | 33 | inp = 3017957 34 | 35 | q1 = deque() 36 | q2 = deque() 37 | 38 | for i in range(1, inp+1): 39 | if i <= inp/2: 40 | q1.append(i) 41 | else: 42 | q2.append(i) 43 | 44 | while len(q1) + len(q2) != 1: 45 | 46 | a = q1.popleft() 47 | 48 | if len(q1) == len(q2): 49 | q1.pop() 50 | else: 51 | q2.popleft() 52 | 53 | q2.append(a) 54 | 55 | q1.append(q2.popleft()) 56 | 57 | print(q1.pop()) 58 | 59 | 60 | if __name__ == "__main__": 61 | 62 | part1() 63 | part2() 64 | -------------------------------------------------------------------------------- /2016/day20/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(time.time()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | 17 | r = [] 18 | 19 | for l in open('input.txt').read().split('\n'): 20 | p = list(map(int, l.split('-'))) 21 | r.append([p[0], p[1]]) 22 | 23 | r.sort() 24 | 25 | for i in range(len(r) - 1): 26 | 27 | if r[i][1] > r[i+1][1]: 28 | r[i+1][1] = r[i][1] 29 | elif r[i+1][0] > r[i][1]: 30 | print(r[i][1]+1) 31 | break 32 | 33 | 34 | @profiler 35 | def part2(): 36 | 37 | r = [] 38 | 39 | for l in open('input.txt').read().split('\n'): 40 | p = list(map(int, l.split('-'))) 41 | r.append([p[0], p[1]]) 42 | 43 | r.sort() 44 | 45 | cnt = 0 46 | 47 | for i in range(len(r) - 1): 48 | 49 | if r[i][1] > r[i+1][1]: 50 | r[i+1][1] = r[i][1] 51 | elif r[i+1][0] > r[i][1]: 52 | cnt += (r[i+1][0] - r[i][1] - 1) 53 | 54 | print(cnt) 55 | 56 | 57 | if __name__ == "__main__": 58 | 59 | part1() 60 | part2() 61 | -------------------------------------------------------------------------------- /2017/day01/code.py: -------------------------------------------------------------------------------- 1 | import time,os 2 | 3 | def profiler(method): 4 | def wrapper_method(*arg, **kw): 5 | t = time.time() 6 | method(*arg, **kw) 7 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 8 | return wrapper_method 9 | 10 | @profiler 11 | def part1(): 12 | 13 | 14 | inp = open('input.txt').read().strip() 15 | 16 | cnt = 0 17 | for i in range(len(inp)): 18 | if inp[i] == inp[(i+1)%len(inp)]: 19 | cnt += int(inp[i]) 20 | 21 | print(cnt) 22 | 23 | 24 | 25 | @profiler 26 | def part2(): 27 | 28 | inp = open('input.txt').read().strip() 29 | 30 | cnt = 0 31 | for i in range(len(inp)): 32 | if inp[i] == inp[(i+len(inp)//2)%len(inp)]: 33 | cnt += int(inp[i]) 34 | 35 | print(cnt) 36 | 37 | if __name__ == "__main__": 38 | 39 | part1() 40 | part2() 41 | -------------------------------------------------------------------------------- /2017/day02/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import os 3 | from itertools import permutations 4 | 5 | 6 | def profiler(method): 7 | def wrapper_method(*arg, **kw): 8 | t = time.time() 9 | method(*arg, **kw) 10 | print('Method ' + method.__name__ + ' took : ' + 11 | "{:2.5f}".format(time.time()-t) + ' sec') 12 | return wrapper_method 13 | 14 | 15 | @profiler 16 | def part1(): 17 | 18 | inp = [] 19 | for l in open('input.txt').read().split('\n'): 20 | inp.append([*map(int, l.split())]) 21 | 22 | total = 0 23 | for l in inp: 24 | total += max(l) - min(l) 25 | 26 | print(total) 27 | 28 | 29 | @profiler 30 | def part2(): 31 | 32 | inp = [] 33 | for l in open('input.txt').read().split('\n'): 34 | inp.append([*map(int, l.split())]) 35 | 36 | total = 0 37 | for l in inp: 38 | for p in permutations(l, 2): 39 | if p[0] % p[1] == 0: 40 | total += p[0] // p[1] 41 | break 42 | print(total) 43 | 44 | 45 | if __name__ == "__main__": 46 | 47 | part1() 48 | part2() 49 | -------------------------------------------------------------------------------- /2017/day03/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import math 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | method(*arg, **kw) 9 | print('Method ' + method.__name__ + ' took : ' + 10 | "{:2.5f}".format(time.time()-t) + ' sec') 11 | return wrapper_method 12 | 13 | @profiler 14 | def part1(): 15 | 16 | inp = 277678 17 | 18 | d = math.ceil(math.sqrt(inp)) 19 | offset = d**2 - inp 20 | 21 | print(int((d-1)/2 + d//2 - offset % (d-1))) 22 | 23 | 24 | @profiler 25 | def part2(): 26 | 27 | inp = 277678 28 | 29 | # https://oeis.org/A141481 30 | # Square spiral of sums of selected 31 | # preceding terms, starting at 1. 32 | 33 | series = [ 34 | 1, 1, 2, 4, 5, 10, 11, 23, 25, 26, 54, 57, 59, 122, 133, 142, 147, 35 | 304, 330, 351, 362, 747, 806, 880, 931, 957, 1968, 2105, 2275, 2391, 36 | 2450, 5022, 5336, 5733, 6155,6444, 6591, 13486, 14267, 15252, 16295, 37 | 17008, 17370, 35487,37402, 39835, 42452, 45220, 47108, 48065, 98098, 38 | 103128,109476, 116247, 123363,128204 ,130654 ,266330 ,279138 , 295229, 39 | 312453 ,330785 ,349975 ,363010 ,369601 ,752688 ,787032 ,830037 ,875851 , 40 | 924406 ,975079 ,1009457 ,1026827 ,2089141 ,2179400 ,2292124 ,2411813 , 41 | 2539320 ,2674100 ,2814493 ,2909666 ,2957731 ,6013560 ,6262851 ,6573553 , 42 | 6902404 ,7251490 ,7619304 ,8001525 ,8260383 ,8391037,17048404 ,17724526 , 43 | 18565223 ,19452043 ,20390510 ,21383723 ,22427493 ,23510079 44 | ] 45 | 46 | for i in series: 47 | if i > inp: 48 | print(i) 49 | break 50 | 51 | if __name__ == "__main__": 52 | 53 | part1() 54 | part2() 55 | -------------------------------------------------------------------------------- /2017/day04/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import math 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | method(*arg, **kw) 9 | print('Method ' + method.__name__ + ' took : ' + 10 | "{:2.5f}".format(time.time()-t) + ' sec') 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | 17 | cnt = 0 18 | for l in open('input.txt'): 19 | p_list = l.strip().split() 20 | p_set = set(p_list) 21 | 22 | if len(p_list) == len(p_set): 23 | cnt += 1 24 | 25 | print(cnt) 26 | 27 | 28 | @profiler 29 | def part2(): 30 | 31 | cnt = 0 32 | for l in open('input.txt'): 33 | p_list = [] 34 | for p in l.strip().split(): 35 | p = list(p) 36 | p.sort() 37 | p_list.append(''.join(p)) 38 | 39 | p_set = set(p_list) 40 | 41 | if len(p_list) == len(p_set): 42 | cnt += 1 43 | 44 | print(cnt) 45 | 46 | 47 | if __name__ == "__main__": 48 | 49 | part1() 50 | part2() 51 | -------------------------------------------------------------------------------- /2017/day05/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import math 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | method(*arg, **kw) 9 | print('Method ' + method.__name__ + ' took : ' + 10 | "{:2.5f}".format(time.time()-t) + ' sec') 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | 17 | inp = [* map(int, open('input.txt').read().strip().split('\n'))] 18 | 19 | pc = 0 20 | steps = 0 21 | 22 | while pc < len(inp): 23 | steps += 1 24 | 25 | inp[pc] += 1 26 | pc += inp[pc] - 1 27 | 28 | print(steps) 29 | 30 | 31 | @profiler 32 | def part2(): 33 | 34 | inp = [* map(int, open('input.txt').read().strip().split('\n'))] 35 | 36 | pc = 0 37 | steps = 0 38 | 39 | while pc < len(inp): 40 | steps += 1 41 | 42 | if inp[pc] >= 3: 43 | inp[pc] -= 1 44 | pc += inp[pc] + 1 45 | else: 46 | inp[pc] += 1 47 | pc += inp[pc] - 1 48 | 49 | print(steps) 50 | 51 | 52 | if __name__ == "__main__": 53 | 54 | part1() 55 | part2() 56 | -------------------------------------------------------------------------------- /2017/day06/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import math 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | method(*arg, **kw) 9 | print('Method ' + method.__name__ + ' took : ' + 10 | "{:2.5f}".format(time.time()-t) + ' sec') 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | 17 | inp = [* map(int, open('input.txt').read().strip().split())] 18 | 19 | seen = set() 20 | 21 | while str(inp) not in seen: 22 | seen.add(str(inp)) 23 | 24 | val = max(inp) 25 | idx = inp.index(val) 26 | inp[idx] = 0 27 | 28 | for i in range(val): 29 | inp[(idx + i + 1) % len(inp)] += 1 30 | 31 | print(len(seen)) 32 | 33 | 34 | @profiler 35 | def part2(): 36 | 37 | inp = [* map(int, open('input.txt').read().strip().split())] 38 | 39 | seen = set() 40 | age = {} 41 | cnt = 0 42 | 43 | while str(inp) not in seen: 44 | seen.add(str(inp)) 45 | 46 | age[str(inp)] = cnt 47 | cnt += 1 48 | 49 | val = max(inp) 50 | idx = inp.index(val) 51 | inp[idx] = 0 52 | 53 | for i in range(val): 54 | inp[(idx + i + 1) % len(inp)] += 1 55 | 56 | print(cnt-age[str(inp)]) 57 | 58 | 59 | if __name__ == "__main__": 60 | 61 | part1() 62 | part2() 63 | -------------------------------------------------------------------------------- /2017/day08/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | from collections import defaultdict 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | method(*arg, **kw) 9 | print('Method ' + method.__name__ + ' took : ' + 10 | "{:2.5f}".format(time.time()-t) + ' sec') 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | 17 | reg = defaultdict(int) 18 | 19 | for l in open('input.txt'): 20 | p = l.strip().split() 21 | val = int(p[2]) if 'inc' in l else -int(p[2]) 22 | 23 | if eval('reg[\''+str(p[-3]) +'\'] ' + ' '.join(p[-2:])): 24 | reg[p[0]] += val 25 | 26 | print(max(reg.values())) 27 | 28 | 29 | @profiler 30 | def part2(): 31 | 32 | reg = defaultdict(int) 33 | highest = 0 34 | 35 | for l in open('input.txt'): 36 | p = l.strip().split() 37 | val = int(p[2]) if 'inc' in l else -int(p[2]) 38 | 39 | if eval('reg[\''+str(p[-3]) +'\'] ' + ' '.join(p[-2:])): 40 | reg[p[0]] += val 41 | if reg[p[0]] > highest: 42 | highest = reg[p[0]] 43 | 44 | print(highest) 45 | 46 | 47 | if __name__ == "__main__": 48 | 49 | part1() 50 | part2() 51 | -------------------------------------------------------------------------------- /2017/day09/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | from collections import defaultdict 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | method(*arg, **kw) 9 | print('Method ' + method.__name__ + ' took : ' + 10 | "{:2.5f}".format(time.time()-t) + ' sec') 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | 17 | inp = open('input.txt').read().strip() 18 | 19 | #inp = '{{}}' 20 | open_groups = 0 21 | score = 0 22 | open_garbage = 0 23 | 24 | while inp.count('!!') > 0: 25 | inp = inp.replace('!!' , '') 26 | 27 | for i in range(len(inp)): 28 | 29 | c = inp[i] 30 | if i > 0 and inp[i-1] == '!' : continue 31 | 32 | if c == '<': 33 | open_garbage += 1 34 | elif c == '>': 35 | open_garbage = 0 36 | if c == '{' and open_garbage == 0: 37 | open_groups += 1 38 | score += open_groups 39 | elif c == '}' and open_garbage == 0: 40 | open_groups -= 1 41 | 42 | assert open_groups >= 0 43 | 44 | 45 | print(score) 46 | 47 | 48 | 49 | @profiler 50 | def part2(): 51 | 52 | inp = open('input.txt').read().strip() 53 | 54 | score = 0 55 | open_garbage = 0 56 | 57 | while inp.count('!!') > 0: 58 | inp = inp.replace('!!' , '') 59 | 60 | for i in range(len(inp)): 61 | 62 | c = inp[i] 63 | if i > 0 and inp[i-1] == '!' : continue 64 | 65 | if c == '<' and open_garbage == 0: 66 | open_garbage = 1 67 | elif c == '>' and open_garbage == 1: 68 | open_garbage = 0 69 | 70 | elif open_garbage == 1 and c != '!': 71 | score += 1 72 | #print(c,end='') 73 | 74 | print(score) 75 | 76 | 77 | if __name__ == "__main__": 78 | 79 | part1() 80 | part2() 81 | -------------------------------------------------------------------------------- /2017/day10/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | from functools import reduce 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | method(*arg, **kw) 9 | print( 10 | "Method " 11 | + method.__name__ 12 | + " took : " 13 | + "{:2.5f}".format(time.time() - t) 14 | + " sec" 15 | ) 16 | 17 | return wrapper_method 18 | 19 | 20 | def reverse_section(circle, pos, l): 21 | for i in range(l // 2): 22 | tmp = circle[(pos + i) % len(circle)] 23 | circle[(pos + i) % len(circle)] = circle[(pos + l - i - 1) % len(circle)] 24 | circle[(pos + l - i - 1) % len(circle)] = tmp 25 | 26 | 27 | @profiler 28 | def part1(): 29 | 30 | inp = list(map(int, open("day10/input.txt").read().split(","))) 31 | circle = list(range(256)) 32 | 33 | skip = 0 34 | pos = 0 35 | 36 | for n in inp: 37 | reverse_section(circle, pos, n) 38 | 39 | pos = (pos + n + skip) % len(circle) 40 | 41 | skip += 1 42 | 43 | print(circle[0] * circle[1]) 44 | 45 | 46 | @profiler 47 | def part2(): 48 | 49 | inp = list(map(ord, open("day10/input.txt").read())) 50 | inp += [17, 31, 73, 47, 23] 51 | 52 | circle = list(range(256)) 53 | 54 | skip = 0 55 | pos = 0 56 | 57 | for _ in range(64): 58 | for n in inp: 59 | reverse_section(circle, pos, n) 60 | 61 | pos = (pos + n + skip) % len(circle) 62 | 63 | skip += 1 64 | 65 | dense_hash = [reduce(lambda a, b: a ^ b, circle[i * 16 + 0 : i * 16 + 16]) for i in range(16)] 66 | 67 | 68 | print("".join(map(lambda d: hex(d)[2:].zfill(2), dense_hash))) 69 | 70 | 71 | if __name__ == "__main__": 72 | 73 | part1() 74 | part2() 75 | -------------------------------------------------------------------------------- /2017/day11/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | from collections import Counter 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | method(*arg, **kw) 9 | print( 10 | "Method " 11 | + method.__name__ 12 | + " took : " 13 | + "{:2.5f}".format(time.time() - t) 14 | + " sec" 15 | ) 16 | 17 | return wrapper_method 18 | 19 | 20 | deltas = { 21 | "n": -1j, 22 | "s": 1j, 23 | "ne": 1, 24 | "nw": -1 - 1j, 25 | "se": 1 + 1j, 26 | "sw": -1, 27 | } 28 | 29 | 30 | @profiler 31 | def part1(): 32 | 33 | inp = open("day11/input.txt").read().split(",") 34 | 35 | pos = 0 36 | for d in inp: 37 | pos += deltas[d] 38 | 39 | print(int(abs(pos.imag) + (pos.real))) 40 | 41 | 42 | @profiler 43 | def part2(): 44 | 45 | inp = open("day11/input.txt").read().split(",") 46 | 47 | pos = 0 48 | ds = [] 49 | for d in inp: 50 | pos += deltas[d] 51 | ds.append(int(abs(pos.imag) + (pos.real))) 52 | 53 | print(max(ds)) 54 | 55 | 56 | if __name__ == "__main__": 57 | 58 | part1() 59 | part2() 60 | -------------------------------------------------------------------------------- /2017/day12/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | from collections import Counter 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | method(*arg, **kw) 9 | print( 10 | "Method " 11 | + method.__name__ 12 | + " took : " 13 | + "{:2.5f}".format(time.time() - t) 14 | + " sec" 15 | ) 16 | 17 | return wrapper_method 18 | 19 | 20 | @profiler 21 | def part1(): 22 | 23 | connections = {} 24 | 25 | for l in open("day12/input.txt").read().split("\n"): 26 | ps = l.split(" <-> ") 27 | connections[int(ps[0])] = list(map(int, ps[1].split(", "))) 28 | 29 | to_visit = [0] 30 | visited = set() 31 | 32 | while len(to_visit) > 0: 33 | c = to_visit.pop() 34 | 35 | visited.add(c) 36 | 37 | for n_c in connections[c]: 38 | if n_c not in visited: 39 | to_visit.append(n_c) 40 | 41 | print(len(visited)) 42 | 43 | 44 | def explore_node(graph, node): 45 | 46 | to_visit = [node] 47 | visited = set() 48 | 49 | while len(to_visit) > 0: 50 | c = to_visit.pop() 51 | 52 | visited.add(c) 53 | 54 | for n_c in graph[c]: 55 | if n_c not in visited: 56 | to_visit.append(n_c) 57 | 58 | return visited 59 | 60 | 61 | @profiler 62 | def part2(): 63 | 64 | connections = {} 65 | 66 | for l in open("day12/input.txt").read().split("\n"): 67 | ps = l.split(" <-> ") 68 | connections[int(ps[0])] = list(map(int, ps[1].split(", "))) 69 | 70 | nodes = set(connections.keys()) 71 | groups = [] 72 | 73 | while len(nodes) > 0: 74 | c = nodes.pop() 75 | t = explore_node(connections, c) 76 | 77 | groups.append(c) 78 | 79 | nodes = nodes - t 80 | 81 | print(len(groups)) 82 | 83 | 84 | if __name__ == "__main__": 85 | 86 | part1() 87 | part2() 88 | -------------------------------------------------------------------------------- /2017/day13/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | from collections import Counter 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | ret = method(*arg, **kw) 9 | print( 10 | "Method " 11 | + method.__name__ 12 | + " took : " 13 | + "{:2.5f}".format(time.time() - t) 14 | + " sec" 15 | ) 16 | return ret 17 | return wrapper_method 18 | 19 | 20 | @profiler 21 | def part1(): 22 | 23 | firewall = {} 24 | 25 | for l in open("day13/input.txt").read().split("\n"): 26 | ps = l.split(": ") 27 | firewall[int(ps[0])] = int(ps[1]) 28 | 29 | print(sum([s * firewall[s] for s in firewall if s%(2*firewall[s] - 2) == 0])) 30 | 31 | 32 | 33 | 34 | @profiler 35 | def part2(): 36 | 37 | firewall = {} 38 | 39 | for l in open("day13/input.txt").read().split("\n"): 40 | ps = l.split(": ") 41 | firewall[int(ps[0])] = int(ps[1]) 42 | 43 | if __name__ == "__main__": 44 | 45 | part1() 46 | part2() 47 | 48 | from itertools import count as c 49 | @profiler 50 | def solve(input): 51 | S = [(d, r, 2*r-2) for d, r in eval(input.strip().replace(*'\n,').join('{}')).items()] 52 | part1 = sum(d*r for d, r, R in S if not d%R) 53 | part2 = next(i for i in c() if all((i+d)%R for d, _, R in S)) 54 | return part1, part2 55 | 56 | print(solve(open("day13/input.txt").read())) 57 | -------------------------------------------------------------------------------- /2017/day15/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | from collections import Counter 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | ret = method(*arg, **kw) 9 | print( 10 | "Method " 11 | + method.__name__ 12 | + " took : " 13 | + "{:2.5f}".format(time.time() - t) 14 | + " sec" 15 | ) 16 | return ret 17 | 18 | return wrapper_method 19 | 20 | 21 | @profiler 22 | def part1(): 23 | 24 | vals = [int(l.split(" ")[-1]) for l in open("day15/input.txt").read().split("\n")] 25 | 26 | rem = 2147483647 27 | factors = [16807, 48271] 28 | 29 | cnt = 0 30 | for _ in range(int(4e7 + 1)): 31 | vals[0] = vals[0] * factors[0] % rem 32 | vals[1] = vals[1] * factors[1] % rem 33 | 34 | if vals[0] & 0xFFFF == vals[1] & 0xFFFF: 35 | cnt += 1 36 | 37 | print(cnt) 38 | 39 | 40 | @profiler 41 | def part2(): 42 | 43 | vals = [int(l.split(" ")[-1]) for l in open("day15/input.txt").read().split("\n")] 44 | 45 | rem = 2147483647 46 | factors = [16807, 48271] 47 | 48 | cnt = 0 49 | for _ in range(int(5e6 + 1)): 50 | while True: 51 | vals[0] = vals[0] * factors[0] % rem 52 | if vals[0] % 4 == 0: 53 | break 54 | 55 | while True: 56 | vals[1] = vals[1] * factors[1] % rem 57 | if vals[1] % 8 == 0: 58 | break 59 | 60 | if vals[0] & 0xFFFF == vals[1] & 0xFFFF: 61 | cnt += 1 62 | 63 | print(cnt) 64 | 65 | 66 | if __name__ == "__main__": 67 | 68 | part1() 69 | part2() 70 | -------------------------------------------------------------------------------- /2017/day17/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | from collections import deque 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | ret = method(*arg, **kw) 9 | print( 10 | "Method " 11 | + method.__name__ 12 | + " took : " 13 | + "{:2.5f}".format(time.time() - t) 14 | + " sec" 15 | ) 16 | return ret 17 | 18 | return wrapper_method 19 | 20 | 21 | input = 314 22 | 23 | 24 | @profiler 25 | def part1(): 26 | 27 | buff = deque([0]) 28 | 29 | pos = 0 30 | for i in range(1, 2017 + 1): 31 | pos = (pos + input) % i 32 | buff.insert(pos + 1, i) 33 | 34 | pos += 1 35 | 36 | print(buff[buff.index(2017) + 1]) 37 | 38 | 39 | @profiler 40 | def part2(): 41 | 42 | pos = 0 43 | for i in range(1, 50000000 + 1): 44 | pos = (pos + input) % i 45 | if pos == 0: 46 | t = i 47 | 48 | pos += 1 49 | 50 | print(t) 51 | 52 | 53 | if __name__ == "__main__": 54 | 55 | part1() 56 | part2() 57 | -------------------------------------------------------------------------------- /2017/day25/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import re 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | ret = method(*arg, **kw) 9 | print("Method " + method.__name__ + " took : " + 10 | "{:2.5f}".format(time.time() - t) + " sec") 11 | return ret 12 | 13 | return wrapper_method 14 | 15 | 16 | @profiler 17 | def part1(): 18 | 19 | input = open("day25/input.txt").read().split("\n\n") 20 | 21 | cycles = int(re.findall(r"\d+", input[0])[0]) 22 | 23 | states = {} 24 | for s in input[1:]: 25 | s = s.splitlines() 26 | 27 | name = s[0][-2] 28 | w_false = int(s[2][-2]) 29 | d_false = 1 if "right" in s[3] else -1 30 | s_false = s[4][-2] 31 | 32 | w_true = int(s[6][-2]) 33 | d_true = 1 if "right" in s[7] else -1 34 | s_true = s[8][-2] 35 | 36 | states[name] = (w_false, d_false, s_false, w_true, d_true, s_true) 37 | 38 | ones = set() 39 | pos = 0 40 | current_state = "A" 41 | 42 | for _ in range(cycles): 43 | if pos not in ones: 44 | if states[current_state][0] == 1: 45 | ones.add(pos) 46 | pos += states[current_state][1] 47 | current_state = states[current_state][2] 48 | else: 49 | if states[current_state][3] == 0: 50 | ones.remove(pos) 51 | pos += states[current_state][4] 52 | current_state = states[current_state][5] 53 | 54 | print(len(ones)) 55 | 56 | 57 | if __name__ == "__main__": 58 | 59 | part1() 60 | -------------------------------------------------------------------------------- /2018/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required (VERSION 3.8) 2 | 3 | project(2018) 4 | 5 | set(CMAKE_INSTALL_PREFIX ${CMAKE_INSTALL_PREFIX}/${CMAKE_PROJECT_NAME}) 6 | 7 | add_subdirectory(day01) 8 | add_subdirectory(day02) 9 | -------------------------------------------------------------------------------- /2018/day01/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.8) 2 | 3 | add_executable(day01 day01.cpp) 4 | 5 | 6 | #install(TARGETS day01 DESTINATION ${CMAKE_CURRENT_BINARY_DIR}/day01) 7 | install(FILES day01_input.txt DESTINATION ${CMAKE_CURRENT_BINARY_DIR}/input/) -------------------------------------------------------------------------------- /2018/day01/day01.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | 7 | uint32_t task_1(std::ifstream input_fd) { 8 | int32_t sum{}, tmp_val{}; 9 | 10 | while (input_fd >> tmp_val) sum += tmp_val; 11 | 12 | return sum; 13 | } 14 | 15 | uint32_t task_2(std::ifstream input_fd) { 16 | int32_t sum{}, tmp_val{}; 17 | std::set freq_set{}; 18 | std::vector freqs; 19 | 20 | while (input_fd >> tmp_val) freqs.emplace_back(tmp_val); 21 | 22 | 23 | while (true) { 24 | for (const auto &tmp_val : freqs) { 25 | sum += tmp_val; 26 | 27 | if (freq_set.find(sum) != freq_set.end()) { 28 | return sum; 29 | } 30 | else { 31 | freq_set.emplace(sum); 32 | } 33 | } 34 | 35 | } 36 | return 0; 37 | 38 | 39 | } 40 | 41 | int main() { 42 | 43 | std::cout << "sum of frequencies in task 1 is : " << task_1(std::ifstream{ "input/day01_input.txt" }) << std::endl; 44 | std::cout << "first repeated frequency in task 2 is : " << task_2(std::ifstream{ "input/day01_input.txt" }) << std::endl; 45 | 46 | return 0; 47 | } 48 | -------------------------------------------------------------------------------- /2018/day02/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.8) 2 | 3 | add_executable(day02 day02.cpp) 4 | 5 | 6 | #install(TARGETS day02 DESTINATION ${CMAKE_CURRENT_BINARY_DIR}/day02) 7 | install(FILES day02_input.txt DESTINATION ${CMAKE_CURRENT_BINARY_DIR}/input/) 8 | -------------------------------------------------------------------------------- /2018/day03/code.py: -------------------------------------------------------------------------------- 1 | import time,os,re 2 | from collections import defaultdict 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | method(*arg, **kw) 8 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 9 | return wrapper_method 10 | 11 | @profiler 12 | def part1(): 13 | 14 | with open('input.txt', 'r') as f_in: 15 | area = defaultdict(lambda : 0) 16 | 17 | for l in f_in: 18 | cid,x,y,w,h = map(int,re.findall(r'\d+' , l)) 19 | for dx in range(x,x+w): 20 | for dy in range(y,y+h): 21 | area[(dx,dy)] += 1 22 | 23 | 24 | print(min(area.values())) 25 | print(len(list(filter( lambda x : x > 1 , area.values())))) 26 | 27 | 28 | @profiler 29 | def part2(): 30 | area = defaultdict(lambda :0) 31 | 32 | with open('input.txt', 'r') as f_in: 33 | 34 | for l in f_in: 35 | cid,x,y,w,h = map(int,re.findall(r'\d+' , l)) 36 | for dx in range(x,x+w): 37 | for dy in range(y,y+h): 38 | area[(dx,dy)] += 1 39 | 40 | with open('input.txt', 'r') as f_in: 41 | for l in f_in: 42 | cid,x,y,w,h = map(int,re.findall(r'\d+' , l)) 43 | overlap = False 44 | for dx in range(x,x+w): 45 | if overlap: 46 | break 47 | for dy in range(y,y+h): 48 | if area[(dx,dy)] > 1 : 49 | overlap = True 50 | break 51 | if not overlap: 52 | print(cid) 53 | break 54 | 55 | 56 | if __name__ == "__main__": 57 | 58 | part1() 59 | part2() 60 | -------------------------------------------------------------------------------- /2018/day05/code.py: -------------------------------------------------------------------------------- 1 | import time,os,re 2 | from collections import defaultdict 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 9 | return ret 10 | return wrapper_method 11 | 12 | @profiler 13 | def part1(): 14 | 15 | st = open('input.txt').read().strip() 16 | 17 | while True: 18 | tmp = st 19 | for i in range(26): 20 | tr = str(chr(ord('a') + i) + chr(ord('A') + i)) 21 | tmp = tmp.replace(tr , '' ) 22 | tmp = tmp.replace(tr[::-1] , '' ) 23 | if tmp == st : 24 | break 25 | st = tmp 26 | print(len(st)) 27 | 28 | 29 | 30 | 31 | @profiler 32 | def part2(): 33 | 34 | input = open('input.txt').read().strip() 35 | ls = [] 36 | 37 | for ch in range(26): 38 | 39 | st = input 40 | st = st.replace(chr(ord('a') + ch) , '') 41 | st = st.replace(chr(ord('A') + ch) , '') 42 | 43 | 44 | while True: 45 | tmp = st 46 | for i in range(26): 47 | tr = str(chr(ord('a') + i) + chr(ord('A') + i)) 48 | tmp = tmp.replace(tr , '' ) 49 | tmp = tmp.replace(tr[::-1] , '' ) 50 | if tmp == st : 51 | break 52 | st = tmp 53 | ls.append(len(st)) 54 | print(min(ls)) 55 | 56 | 57 | 58 | if __name__ == "__main__": 59 | 60 | part1() 61 | part2() 62 | -------------------------------------------------------------------------------- /2018/day07/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | from collections import defaultdict 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(time.time()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | 14 | 15 | @profiler 16 | def both_part(): 17 | workers_count = 5 18 | overhead = 60 19 | 20 | needs = defaultdict(set) 21 | letters = set() 22 | for l in open('input.txt'): 23 | needs[l[36]].add(l[5]) 24 | letters |= set([l[36], l[5]]) 25 | 26 | t = 0 27 | ret = '' 28 | time = {} 29 | workers = [None] * workers_count 30 | 31 | while len(ret) < len(letters): 32 | ready = [] 33 | if workers.count(None) > 0: 34 | for l in letters: 35 | if len(needs[l]) == 0 and l not in ret and l not in workers: 36 | ready.append(l) 37 | 38 | ready.sort() 39 | for _ in range(min(workers.count(None),len(ready))): 40 | ch = ready.pop(0) 41 | workers[workers.index(None)] = ch 42 | time[ch] = t 43 | 44 | t += 1 45 | 46 | for ele in workers: 47 | if ele is not None and t - time[ele] == overhead + ord(ele) - ord('A') + 1: 48 | ret += ele 49 | workers[workers.index(ele)] = None 50 | for tmp in needs: 51 | needs[tmp] -= set(ele) 52 | 53 | print(ret , t) 54 | 55 | 56 | if __name__ == "__main__": 57 | 58 | both_part() 59 | -------------------------------------------------------------------------------- /2018/day08/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | 3 | def profiler(method): 4 | def wrapper_method(*arg, **kw): 5 | t = time.time() 6 | ret = method(*arg, **kw) 7 | print('Method ' + method.__name__ + ' took : ' + 8 | "{:2.5f}".format(time.time()-t) + ' sec') 9 | return ret 10 | return wrapper_method 11 | 12 | 13 | def get_meta_sum(l): 14 | child_cnt = l.pop(0) 15 | meta_cnt = l.pop(0) 16 | 17 | return sum(get_meta_sum(l) for _ in range(child_cnt)) + sum(l.pop(0) for _ in range(meta_cnt)) 18 | 19 | def get_meta_val(l): 20 | child_cnt = l.pop(0) 21 | meta_cnt = l.pop(0) 22 | 23 | childs_val = [get_meta_val(l) for _ in range(child_cnt)] 24 | metas = [l.pop(0) for _ in range(meta_cnt)] 25 | 26 | if child_cnt == 0 : 27 | ret = sum(metas) 28 | else : 29 | ret = 0 30 | for i in metas : 31 | if i-1 < child_cnt: 32 | ret += childs_val[i-1] 33 | 34 | return ret 35 | 36 | @profiler 37 | def part_1(): 38 | d = list(map(int,open('input.txt').read().split())) 39 | print(get_meta_sum(d)) 40 | 41 | @profiler 42 | def part_2(): 43 | d = list(map(int,open('input.txt').read().split())) 44 | print(get_meta_val(d)) 45 | 46 | 47 | if __name__ == "__main__": 48 | 49 | part_1() 50 | part_2() 51 | -------------------------------------------------------------------------------- /2018/day10/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import re 3 | import math 4 | 5 | 6 | def profiler(method): 7 | def wrapper_method(*arg, **kw): 8 | t = time.time() 9 | ret = method(*arg, **kw) 10 | print( 11 | "Method " 12 | + method.__name__ 13 | + " took : " 14 | + "{:2.5f}".format(time.time() - t) 15 | + " sec" 16 | ) 17 | return ret 18 | 19 | return wrapper_method 20 | 21 | 22 | def sim(p, t): 23 | return (p[0] + p[2] * t, p[1] + p[3] * t) 24 | 25 | 26 | @profiler 27 | def part_1_2(): 28 | particles = [] 29 | for l in open("day10/input.txt"): 30 | particles.append(tuple(map(int, re.findall(r"(-?\d+)", l.strip())))) 31 | 32 | t = 0 33 | 34 | d = set(map(lambda p: sim(p, 0), particles)) 35 | entropy = (max([p[0] for p in d]) - min([p[0] for p in d])) * ( 36 | max([p[1] for p in d]) - min([p[1] for p in d]) 37 | ) 38 | while True: 39 | t += 1 40 | n_d = set(map(lambda p: sim(p, t), particles)) 41 | n_entropy = (max([p[0] for p in n_d]) - min([p[0] for p in n_d])) * ( 42 | max([p[1] for p in n_d]) - min([p[1] for p in n_d]) 43 | ) 44 | 45 | if n_entropy > entropy: 46 | break 47 | d = n_d 48 | entropy = n_entropy 49 | 50 | print(max([p[0] for p in d]), min([p[0] for p in d])) 51 | for y in range(min([p[1] for p in d]), max([p[1] for p in d]) + 1): 52 | for x in range(min([p[0] for p in d]), max([p[0] for p in d]) + 1): 53 | if (x, y) in d: 54 | print("#", end="") 55 | else: 56 | print(" ", end="") 57 | print() 58 | print(t - 1) 59 | 60 | 61 | if __name__ == "__main__": 62 | 63 | part_1_2() 64 | -------------------------------------------------------------------------------- /2018/day14/code.py: -------------------------------------------------------------------------------- 1 | from collections import Counter 2 | import time 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | ret = method(*arg, **kw) 9 | print("Method " + method.__name__ + " took : " + 10 | "{:2.5f}".format(time.time() - t) + " sec") 11 | return ret 12 | 13 | return wrapper_method 14 | 15 | 16 | @profiler 17 | def part_1(): 18 | input = 652601 19 | score = [3, 7] 20 | 21 | e1 = 0 22 | e2 = 1 23 | 24 | while len(score) - 10 < input: 25 | s = score[e1] + score[e2] 26 | score.extend([int(i) for i in str(s)]) 27 | 28 | e1 = (e1 + 1 + score[e1]) % len(score) 29 | e2 = (e2 + 1 + score[e2]) % len(score) 30 | 31 | print("".join(str(s) for s in score[input:input+10])) 32 | 33 | 34 | @profiler 35 | def part_2(): 36 | input = 652601 37 | score = [3, 7] 38 | 39 | e1 = 0 40 | e2 = 1 41 | 42 | while str(input) not in "".join(str(x) for x in score[-(len(str(input)) + 1):]): 43 | s = score[e1] + score[e2] 44 | score.extend([int(i) for i in str(s)]) 45 | 46 | e1 = (e1 + 1 + score[e1]) % len(score) 47 | e2 = (e2 + 1 + score[e2]) % len(score) 48 | 49 | l = "".join(str(x) for x in score[-(len(str(input)) + 1):]).replace(str(input) , "") 50 | 51 | 52 | print(len(score) - len(str(input)) - len(l)) 53 | 54 | 55 | if __name__ == "__main__": 56 | 57 | part_1() 58 | part_2() 59 | -------------------------------------------------------------------------------- /2018/day21/code.py: -------------------------------------------------------------------------------- 1 | # pylint: disable=C0114, C0116, C0209 2 | 3 | import time 4 | import heapq 5 | 6 | DEPTH = 10647 7 | TARGET = (7, 770) 8 | 9 | # DEPTH = 510 10 | # TARGET = (10, 10) 11 | 12 | 13 | def profiler(method): 14 | def wrapper_method(*arg, **kw): 15 | t = time.time() 16 | ret = method(*arg, **kw) 17 | print("Method " + method.__name__ + " took : " + "{:2.5f}".format(time.time() - t) + " sec") 18 | return ret 19 | 20 | return wrapper_method 21 | 22 | @profiler 23 | def part_1(): 24 | t = int(open("day21/input.txt","r").readlines()[8].split()[1]) 25 | 26 | r = [0]*6 27 | 28 | while True: 29 | r[0] = r[2] | 65536 30 | r[2] = t 31 | 32 | while True: 33 | r[2] = (((r[2] + (r[0] & 255)) & 16777215) * 65899) & 16777215 34 | if 256 > r[0]: 35 | print(r[2]) 36 | return 37 | else: 38 | r[0] //= 256 39 | 40 | 41 | @profiler 42 | def part_2(): 43 | 44 | r = [0]*6 45 | r[5] = int(open("day21/input.txt","r").readlines()[8].split()[1]) 46 | r2s = [] 47 | 48 | while True: 49 | r[0] = r[2] | 65536 50 | r[2] = r[5] 51 | 52 | while True: 53 | # 255:10 , 16777215 :12 , 65899 : 13 , 16777215 : 14 54 | # assuming hard coded except for line 8 55 | r[2] = (((r[2] + (r[0] & 255)) & 16777215) * 65899) & 16777215 56 | if 256 > r[0]: 57 | if r[2] in r2s: # loop starting 58 | print(r2s[-1]) 59 | return 60 | else: 61 | r2s.append(r[2]) 62 | break 63 | else: 64 | r[0] //= 256 65 | 66 | 67 | if __name__ == "__main__": 68 | part_1() 69 | part_2() 70 | -------------------------------------------------------------------------------- /2018/day23/code.py: -------------------------------------------------------------------------------- 1 | # pylint: disable=C0114,C0116,C0301,C0209,W1514,C0414,C0103 2 | 3 | import time 4 | import re 5 | import heapq 6 | 7 | 8 | def profiler(method): 9 | def wrapper_method(*arg, **kw): 10 | t = time.time() 11 | ret = method(*arg, **kw) 12 | print("Method " + method.__name__ + " took : " + 13 | "{:2.5f}".format(time.time() - t) + " sec") 14 | return ret 15 | 16 | return wrapper_method 17 | 18 | 19 | def get_dst(p1, p2): 20 | return sum(abs(p1[i] - p2[i]) for i in range(3)) 21 | 22 | 23 | def get_in_range(bots, b): 24 | return sum(get_dst(p[0], b[0]) <= b[1] for p in bots) 25 | 26 | 27 | @profiler 28 | def part_1(): 29 | bots = [] 30 | max_b = ((0, 0, 0), -1) 31 | for l in open("day23/input.txt").read().splitlines(): 32 | p = re.findall(r"-?\d+", l) 33 | bots.append((((int(p[0]), int(p[1]), int(p[2])), int(p[3])))) 34 | if int(p[3]) > max_b[1]: 35 | max_b = bots[-1] 36 | 37 | print(get_in_range(bots, max_b)) 38 | 39 | 40 | @profiler 41 | def part_2(): 42 | 43 | h = [] 44 | 45 | for l in open("day23/input.txt").read().splitlines(): 46 | p = re.findall(r"-?\d+", l) 47 | 48 | x, y, z, r = int(p[0]), int(p[1]), int(p[2]), int(p[3]) 49 | d = abs(x) + abs(y) + abs(z) 50 | 51 | heapq.heappush(h, (d - r, 1)) 52 | heapq.heappush(h, (d + r, -1)) 53 | 54 | count = 0 55 | max_count = 0 56 | result = 0 57 | 58 | while h: 59 | dist, e = heapq.heappop(h) 60 | count += e 61 | if count > max_count: 62 | result = dist 63 | max_count = count 64 | print(result) 65 | 66 | 67 | if __name__ == "__main__": 68 | 69 | part_1() 70 | part_2() 71 | -------------------------------------------------------------------------------- /2018/day25/code.py: -------------------------------------------------------------------------------- 1 | from collections import defaultdict, deque 2 | import time 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | ret = method(*arg, **kw) 9 | print("Method " + method.__name__ + " took : " + 10 | "{:2.5f}".format(time.time() - t) + " sec") 11 | return ret 12 | 13 | return wrapper_method 14 | 15 | 16 | def get_dst(p1, p2): 17 | return sum(abs(p1[i] - p2[i]) for i in range(4)) 18 | 19 | 20 | @profiler 21 | def part_1(): 22 | pts = [tuple(map(int, l.split(","))) 23 | for l in open("input.txt").read().splitlines()] 24 | 25 | grid = defaultdict(set) 26 | 27 | for p1 in pts: 28 | for p2 in pts: 29 | if p1 == p2: 30 | continue 31 | if get_dst(p1,p2) <= 3: 32 | grid[p1].add(p2) 33 | 34 | visited = defaultdict(bool) 35 | cc = 0 36 | 37 | for p in pts: 38 | if visited[p] == False: 39 | 40 | to_visit = deque() 41 | to_visit.append(p) 42 | 43 | while to_visit: 44 | current_pt = to_visit.popleft() 45 | 46 | visited[current_pt] = True 47 | 48 | for np in grid[current_pt]: 49 | if visited[np] == False: 50 | to_visit.append(np) 51 | 52 | cc += 1 53 | 54 | print(cc) 55 | 56 | 57 | if __name__ == "__main__": 58 | 59 | part_1() 60 | -------------------------------------------------------------------------------- /2019/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required (VERSION 3.8) 2 | 3 | project(2019) 4 | 5 | set(CMAKE_CXX_STANDARD 17) 6 | set(CMAKE_CXX_STANDARD_REQUIRED ON) 7 | set(CMAKE_INSTALL_PREFIX "${CMAKE_BINARY_DIR}/install") 8 | 9 | 10 | add_subdirectory(day01) 11 | add_subdirectory(day02) 12 | add_subdirectory(day03) 13 | add_subdirectory(day04) 14 | add_subdirectory(day05) 15 | add_subdirectory(day06) 16 | add_subdirectory(day07) 17 | add_subdirectory(day08) 18 | add_subdirectory(day09) 19 | add_subdirectory(day10) 20 | add_subdirectory(day11) 21 | add_subdirectory(day12) 22 | add_subdirectory(day13) 23 | add_subdirectory(day14) 24 | add_subdirectory(day15) 25 | add_subdirectory(day16) 26 | add_subdirectory(day17) 27 | add_subdirectory(day18) 28 | add_subdirectory(day19) 29 | #add_subdirectory(day20) 30 | add_subdirectory(day21) 31 | add_subdirectory(day22) 32 | add_subdirectory(day23) 33 | add_subdirectory(day24) 34 | add_subdirectory(day25) 35 | -------------------------------------------------------------------------------- /2019/day01/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.0) 2 | 3 | add_executable(day01 day.cpp) 4 | 5 | install(TARGETS day01 DESTINATION day01) 6 | install(FILES input.txt DESTINATION day01/input/) -------------------------------------------------------------------------------- /2019/day01/day.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | uint32_t getFuelReq(uint32_t mass) { 6 | return mass / 3 > 2 ? ((mass / 3) - 2) : 0; 7 | } 8 | 9 | 10 | uint32_t task_1(std::ifstream input_fd) { 11 | uint32_t sum{}; 12 | uint32_t tmp_val{}; 13 | 14 | while (input_fd >> tmp_val) sum += getFuelReq(tmp_val); 15 | 16 | return sum; 17 | } 18 | 19 | uint32_t task_2(std::ifstream input_fd) { 20 | int32_t sum{6}, input_val{}; 21 | 22 | while (input_fd >> input_val) { 23 | while (input_val > 0) { 24 | uint32_t tmp_val = getFuelReq(input_val); 25 | sum += tmp_val; 26 | input_val = tmp_val; 27 | } 28 | } 29 | 30 | return sum; 31 | } 32 | 33 | int main() { 34 | 35 | std::cout << "sum of fuel mass ins task 1 is : " << task_1(std::ifstream{ "input/input.txt" }) << std::endl; 36 | std::cout << "sum of fuel mass ins task 2 is : " << task_2(std::ifstream{ "input/input.txt" }) << std::endl; 37 | 38 | return 0; 39 | } 40 | -------------------------------------------------------------------------------- /2019/day01/day1.go: -------------------------------------------------------------------------------- 1 | package main 2 | 3 | import ( 4 | "bufio" 5 | "fmt" 6 | "os" 7 | "strconv" 8 | ) 9 | 10 | func main() { 11 | 12 | file, _ := os.Open("day1_input.txt") 13 | 14 | defer file.Close() 15 | scanner := bufio.NewScanner(file) 16 | 17 | var sum1, sum2 = 0, 0 18 | for scanner.Scan() { 19 | mod, _ := strconv.Atoi(scanner.Text()) 20 | if mod/3 > 2 { 21 | sum1 += (mod / 3) - 2 22 | } 23 | 24 | for mod/3 > 2 { 25 | tmp := (mod / 3) - 2 26 | sum2 += tmp 27 | mod = tmp 28 | } 29 | 30 | } 31 | fmt.Println(sum1, sum2) 32 | 33 | } 34 | -------------------------------------------------------------------------------- /2019/day02/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.0) 2 | 3 | add_executable(day02 day.cpp) 4 | 5 | install(TARGETS day02 DESTINATION day02) 6 | install(FILES input.txt DESTINATION day02/input) -------------------------------------------------------------------------------- /2019/day03/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day03 day.cpp) 2 | 3 | install(TARGETS day03 DESTINATION day03) 4 | install(FILES input.txt DESTINATION day03/input) -------------------------------------------------------------------------------- /2019/day04/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day04 day.cpp) 2 | 3 | install(TARGETS day04 DESTINATION day04) 4 | -------------------------------------------------------------------------------- /2019/day05/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day05 day.cpp) 2 | 3 | install(TARGETS day05 DESTINATION day05) 4 | install(FILES input.txt DESTINATION day05/input) -------------------------------------------------------------------------------- /2019/day06/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day06 day.cpp) 2 | 3 | install(TARGETS day06 DESTINATION day06) 4 | install(FILES input.txt DESTINATION day06/input) 5 | -------------------------------------------------------------------------------- /2019/day07/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day07 day.cpp) 2 | 3 | install(TARGETS day07 DESTINATION day07) 4 | install(FILES input.txt DESTINATION day07/input) -------------------------------------------------------------------------------- /2019/day08/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day08 day.cpp) 2 | 3 | install(TARGETS day08 DESTINATION day08) 4 | install(FILES input.txt DESTINATION day08/input) -------------------------------------------------------------------------------- /2019/day09/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day09 day.cpp) 2 | 3 | install(TARGETS day09 DESTINATION day09) 4 | install(FILES input.txt DESTINATION day09/input) -------------------------------------------------------------------------------- /2019/day10/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day10 day10.cpp) 2 | 3 | install(TARGETS day10 DESTINATION day10) 4 | install(FILES day10_input.txt DESTINATION day10/input) -------------------------------------------------------------------------------- /2019/day11/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day11 day11.cpp) 2 | 3 | install(TARGETS day11 DESTINATION day11) 4 | install(FILES day11_input.txt DESTINATION day11/input) -------------------------------------------------------------------------------- /2019/day12/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day12 day12.cpp) 2 | 3 | install(TARGETS day12 DESTINATION day12) -------------------------------------------------------------------------------- /2019/day13/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day13 day13.cpp) 2 | 3 | install(TARGETS day13 DESTINATION day13) 4 | install(FILES day13_input.txt DESTINATION day13/input) -------------------------------------------------------------------------------- /2019/day14/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day14 day14.cpp) 2 | 3 | install(TARGETS day14 DESTINATION day14) 4 | install(FILES day14_input.txt DESTINATION day14/input) -------------------------------------------------------------------------------- /2019/day15/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day15 day15.cpp) 2 | 3 | install(TARGETS day15 DESTINATION day15) 4 | install(FILES day15_input.txt DESTINATION day15/input) -------------------------------------------------------------------------------- /2019/day16/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day16 day16.cpp) 2 | 3 | install(TARGETS day16 DESTINATION day16) 4 | install(FILES day16_input.txt DESTINATION day16/input) -------------------------------------------------------------------------------- /2019/day17/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day17 day17.cpp) 2 | 3 | install(TARGETS day17 DESTINATION day17) 4 | install(FILES day17_input.txt DESTINATION day17/input) -------------------------------------------------------------------------------- /2019/day18/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day18 day18.cpp) 2 | 3 | install(TARGETS day18 DESTINATION day18) 4 | install(FILES day18_input.txt DESTINATION day18/input) 5 | -------------------------------------------------------------------------------- /2019/day19/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day19 day19.cpp) 2 | 3 | install(TARGETS day19 DESTINATION day19) 4 | install(FILES day19_input.txt DESTINATION day19/input) -------------------------------------------------------------------------------- /2019/day20/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day20 day20.cpp) 2 | 3 | install(TARGETS day20 DESTINATION day20) 4 | install(FILES day20_input.txt DESTINATION day20/input) -------------------------------------------------------------------------------- /2019/day21/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day21 day21.cpp) 2 | 3 | install(TARGETS day21 DESTINATION day21) 4 | install(FILES day21_input.txt DESTINATION day21/input) 5 | -------------------------------------------------------------------------------- /2019/day22/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day22 day22.cpp) 2 | 3 | install(TARGETS day22 DESTINATION day22) 4 | install(FILES day22_input.txt DESTINATION day22/input) 5 | -------------------------------------------------------------------------------- /2019/day23/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day23 day23.cpp) 2 | 3 | install(TARGETS day23 DESTINATION day23) 4 | install(FILES day23_input.txt DESTINATION day23/input) 5 | -------------------------------------------------------------------------------- /2019/day24/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day24 day24.cpp) 2 | 3 | install(TARGETS day24 DESTINATION day24) 4 | install(FILES day24_input.txt DESTINATION day24/input) 5 | -------------------------------------------------------------------------------- /2019/day25/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(day25 day25.cpp) 2 | 3 | install(TARGETS day25 DESTINATION day25) 4 | install(FILES day25_input.txt DESTINATION day25/input) -------------------------------------------------------------------------------- /2019/dayxx/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(dayxx dayxx.cpp) 2 | 3 | install(TARGETS dayxx DESTINATION dayxx) 4 | install(FILES dayxx_input.txt DESTINATION dayxx/input) -------------------------------------------------------------------------------- /2019/dayxx/dayxx.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | 7 | class timer { 8 | public: 9 | timer(std::string point) { 10 | m_start_point = std::chrono::high_resolution_clock::now(); 11 | m_point = point; 12 | } 13 | 14 | ~timer() { 15 | auto endclock = std::chrono::high_resolution_clock::now(); 16 | auto start = std::chrono::time_point_cast(m_start_point).time_since_epoch().count(); 17 | auto end = std::chrono::time_point_cast(endclock).time_since_epoch().count(); 18 | 19 | auto duration = end - start; 20 | double ms = duration * 0.001; 21 | 22 | std::cout << "time used by : " << m_point << " was : " << ms << " ms" << std::endl; 23 | 24 | } 25 | 26 | private: 27 | std::string m_point; 28 | std::chrono::time_point m_start_point; 29 | }; 30 | 31 | std::vector string2vector(std::string input_txt) { 32 | std::vector ret; 33 | size_t pos{}; 34 | uint16_t cmd_instance{}; 35 | while ((pos = input_txt.find(',')) != std::string::npos) { 36 | ret.push_back(input_txt.substr(0, pos)); 37 | input_txt.erase(0, pos + 1); 38 | } 39 | ret.push_back(input_txt.substr(0, pos)); 40 | return ret; 41 | } 42 | 43 | void task_1() { 44 | 45 | } 46 | 47 | void task_2(){ 48 | 49 | 50 | } 51 | 52 | int main() { 53 | std::ifstream input_fd{ "input\\day5_input.txt" }; 54 | 55 | 56 | 57 | { 58 | timer t1("task 1"); 59 | task_1(); 60 | } 61 | 62 | { 63 | timer t1("task 2"); 64 | task_2(); 65 | } 66 | 67 | return 0; 68 | } 69 | -------------------------------------------------------------------------------- /2020/.gitignore: -------------------------------------------------------------------------------- 1 | */.vscode/* -------------------------------------------------------------------------------- /2020/day01/code.py: -------------------------------------------------------------------------------- 1 | import time,os 2 | 3 | def profiler(method): 4 | def wrapper_method(*arg, **kw): 5 | t = time.time() 6 | method(*arg, **kw) 7 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 8 | return wrapper_method 9 | 10 | target_val = 2020 11 | 12 | @profiler 13 | def part1(): 14 | 15 | ls = None 16 | 17 | with open('input.txt', 'r') as f_in : 18 | ls = [int(l) for l in f_in] 19 | 20 | for i in range(len(ls)): 21 | if target_val - ls[i] in ls: 22 | print("answer part 1 : " + str(ls[i] * ( target_val - ls[i]))) 23 | return 24 | 25 | 26 | @profiler 27 | def part2(): 28 | 29 | ls = None 30 | 31 | with open('input.txt', 'r') as f_in : 32 | ls = [int(l) for l in f_in] 33 | 34 | for a in range(len(ls)): 35 | for b in range(len(ls)): 36 | if a == b : 37 | continue 38 | tmp_sum = ls[a] + ls[b] 39 | 40 | if target_val - tmp_sum in ls: 41 | print("answer part 2 : " + str(ls[a] * ls[b] * (target_val - tmp_sum))) 42 | return 43 | 44 | if __name__ == "__main__": 45 | 46 | part1() 47 | part2() 48 | -------------------------------------------------------------------------------- /2020/day02/code.py: -------------------------------------------------------------------------------- 1 | import time,os 2 | import re 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | method(*arg, **kw) 8 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 9 | return wrapper_method 10 | 11 | @profiler 12 | def part1(): 13 | 14 | cnt = 0 15 | with open('input.txt', 'r') as f_in: 16 | for l in f_in: 17 | lim = re.findall(r'\d+' , l) 18 | ch = l [l.find(':') - 1] 19 | password = l [l.find(':') +1:].strip() 20 | if int(lim[0]) <= password.count(ch) and password.count(ch) <= int(lim[1]): 21 | cnt += 1 22 | print("part 1 answer : " + str(cnt)) 23 | 24 | 25 | @profiler 26 | def part2(): 27 | with open('input.txt', 'r') as f_in: 28 | cnt = 0 29 | with open('input.txt', 'r') as f_in: 30 | for l in f_in: 31 | pos = re.findall(r'\d+' , l) 32 | ch = l [l.find(':') - 1] 33 | password = l [l.find(':') +1:].strip() 34 | min = False 35 | max = False 36 | 37 | if int(pos[0]) <= len(password): 38 | min = password[int(pos[0]) - 1] == ch 39 | 40 | if int(pos[1]) <= len(password): 41 | max = password[int(pos[1]) - 1] == ch 42 | 43 | if min != max: 44 | cnt += 1 45 | print("part 2 answer : " + str(cnt)) 46 | 47 | if __name__ == "__main__": 48 | 49 | 50 | part1() 51 | part2() 52 | -------------------------------------------------------------------------------- /2020/day03/code.py: -------------------------------------------------------------------------------- 1 | import time,os,re 2 | 3 | def profiler(method): 4 | def wrapper_method(*arg, **kw): 5 | t = time.time() 6 | method(*arg, **kw) 7 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 8 | return wrapper_method 9 | 10 | @profiler 11 | def part1(): 12 | 13 | cnt = 0 14 | dx , dy = (3,1) 15 | with open('input.txt', 'r') as f_in: 16 | for l_idx,l in enumerate(f_in): 17 | if l[(dx * l_idx) % len(l.strip())] == '#': 18 | cnt += 1 19 | print("part 1 : " ,cnt) 20 | 21 | 22 | @profiler 23 | def part2(): 24 | 25 | 26 | trials = [(1,1) , (3,1) , (5,1) , (7,1) , (1,2)] 27 | prod = 1 28 | for dx, dy in trials: 29 | with open('input.txt', 'r') as f_in: 30 | cnt = 0 31 | for l_idx,l in enumerate(f_in): 32 | if l_idx % dy != 0: 33 | continue 34 | if l[(dx * l_idx) % len(l.strip())] == '#': 35 | cnt += 1 36 | prod *= cnt 37 | print("part 2 : " ,prod) 38 | 39 | if __name__ == "__main__": 40 | 41 | part1() 42 | part2() -------------------------------------------------------------------------------- /2020/day05/code.py: -------------------------------------------------------------------------------- 1 | import time,os 2 | import math 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 9 | return ret 10 | return wrapper_method 11 | 12 | 13 | @profiler 14 | def part1(): 15 | ids = [] 16 | with open('input.txt', 'r') as f_in: 17 | for l in f_in: 18 | row_upp = 127 19 | row_low = 0 20 | col_upp = 7 21 | col_low = 0 22 | for dy in l[0:7]: 23 | if dy == 'F': 24 | row_upp = int((row_upp + row_low) / 2.0) 25 | elif dy == 'B': 26 | row_low = int(math.ceil((row_upp + row_low) / 2.0)) 27 | 28 | for dx in l[7:10]: 29 | if dx == 'L': 30 | col_upp = int((col_upp + col_low) / 2.0) 31 | elif dx == 'R': 32 | col_low = int(math.ceil((col_upp + col_low) / 2.0)) 33 | 34 | ids.append(row_low * 8 + col_low) 35 | print('part 1 answer : ' , max(ids)) 36 | return ids 37 | 38 | 39 | @profiler 40 | def part2(ids): 41 | ids.sort() 42 | for i, idx in enumerate(ids): 43 | if 6 < idx < (127*8) and (idx - ids[i - 1]) == 2: 44 | print('part 2 answer : ' , idx - 1) 45 | break 46 | 47 | if __name__ == "__main__": 48 | 49 | ids = part1() 50 | part2(ids) 51 | 52 | 53 | -------------------------------------------------------------------------------- /2020/day06/code.py: -------------------------------------------------------------------------------- 1 | import time,os 2 | from functools import reduce 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | method(*arg, **kw) 8 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 9 | return wrapper_method 10 | 11 | @profiler 12 | def part1(): 13 | 14 | with open('input.txt', 'r') as f_in: 15 | print('part 1 answer : ' , sum(map(len, [set(t.replace('\n' , '')) for t in f_in.read().split('\n\n')]))) 16 | 17 | 18 | @profiler 19 | def part2(): 20 | with open('input.txt', 'r') as f_in: 21 | ls = f_in.read().split('\n\n') 22 | 23 | cnt = 0 24 | for gr in ls: 25 | indvs = gr.split('\n') 26 | tmp = set(indvs[0]) 27 | 28 | for indv in indvs[1:] : 29 | tmp &= set(indv) 30 | cnt += len(tmp) 31 | 32 | print('part 2 answer : ' , cnt) 33 | 34 | if __name__ == "__main__": 35 | 36 | part1() 37 | part2() 38 | -------------------------------------------------------------------------------- /2020/day07/code.py: -------------------------------------------------------------------------------- 1 | import time,os,re 2 | 3 | def profiler(method): 4 | def wrapper_method(*arg, **kw): 5 | t = time.time() 6 | ret = method(*arg, **kw) 7 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 8 | return ret 9 | return wrapper_method 10 | 11 | target_color = 'shiny gold' 12 | 13 | bags = {} 14 | bags_count = {} 15 | 16 | def contains_target(color): 17 | if color is None or bags[color] is None: 18 | return False 19 | elif target_color in bags[color] : 20 | return True 21 | else: 22 | return any(map(contains_target , bags[color])) 23 | 24 | @profiler 25 | def part1(): 26 | 27 | with open('input.txt', 'r') as f_in: 28 | for l in f_in: 29 | color = re.search(r'^\w+ \w+' , l) 30 | if 'no other bags' in l: 31 | bags[color.group(0)] = None 32 | else: 33 | bags[color.group(0)] =re.findall(r'\d+ (\w+ \w+)' , l) 34 | bags_count[color.group(0)] = list(map(int,re.findall(r'(\d+)' , l))) 35 | 36 | cnt = 0 37 | for bag_color in bags: 38 | if contains_target(bag_color): 39 | cnt += 1 40 | 41 | print('part 1 answer : ' , cnt) 42 | 43 | def get_content_count(color): 44 | cnt = 0 45 | 46 | for cr_cnt , cr_color in zip(bags_count[color] , bags[color]): 47 | 48 | if bags[cr_color] is not None: 49 | cnt += cr_cnt + cr_cnt * get_content_count(cr_color) 50 | else : 51 | cnt += cr_cnt 52 | 53 | return cnt 54 | 55 | 56 | @profiler 57 | def part2(): 58 | print('part 2 answer : ' , get_content_count(target_color)) 59 | 60 | 61 | if __name__ == "__main__": 62 | 63 | part1() 64 | part2() 65 | -------------------------------------------------------------------------------- /2020/day09/code.py: -------------------------------------------------------------------------------- 1 | import time,os 2 | 3 | def profiler(method): 4 | def wrapper_method(*arg, **kw): 5 | t = time.time() 6 | ret = method(*arg, **kw) 7 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 8 | return ret 9 | return wrapper_method 10 | 11 | @profiler 12 | def part1(): 13 | 14 | pre_len = 25 15 | 16 | with open('input.txt', 'r') as f_in: 17 | input = [int(l) for l in f_in] 18 | 19 | for i in range(pre_len, len(input)): 20 | found = False 21 | for a in range(i - pre_len, i): 22 | for b in range( a + 1 , i ): 23 | if input[a] + input[b] == input[i]: 24 | found = True 25 | break 26 | if found : 27 | break 28 | if not found: 29 | print('part 1 answer : ' , input[i]) 30 | return input[i] 31 | 32 | 33 | @profiler 34 | def part2(target): 35 | with open('input.txt', 'r') as f_in: 36 | input = [int(l) for l in f_in] 37 | 38 | highest = max(input) 39 | 40 | for i in range(len(input)): 41 | sum = input[i] 42 | hi = 0 43 | lo = highest 44 | 45 | for a in range(i+1 , len(input)): 46 | sum += input[a] 47 | 48 | if input[a] > hi: 49 | hi = input[a] 50 | if input[a] < lo: 51 | lo = input[a] 52 | 53 | if sum > target : 54 | break 55 | elif sum == target: 56 | print('part 2 answer : ' , hi + lo) 57 | return 58 | 59 | 60 | if __name__ == "__main__": 61 | 62 | target = part1() 63 | part2(target) 64 | -------------------------------------------------------------------------------- /2020/day10/code.py: -------------------------------------------------------------------------------- 1 | import time,os 2 | from collections import defaultdict 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret =method(*arg, **kw) 8 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 9 | return ret 10 | return wrapper_method 11 | 12 | @profiler 13 | def part1(): 14 | 15 | l = [int(tmp.strip()) for tmp in open('input.txt', 'r').readlines()] 16 | 17 | l.sort() 18 | 19 | d1 = 1 20 | d3 = 1 21 | 22 | for i in range(1, len(l)): 23 | if l[i] - l[i - 1 ] == 1: 24 | d1 +=1 25 | elif l[i] - l[i - 1 ] == 3 : 26 | d3 += 1 27 | else : 28 | print(l[i] - l[i - 1 ]) 29 | 30 | print('part 1 answer : ' , d1*d3) 31 | 32 | 33 | @profiler 34 | def part2(): 35 | 36 | l = [int(tmp.strip()) for tmp in open('input.txt', 'r').readlines()] 37 | 38 | dev = max(l) + 3 39 | 40 | l.append(0) 41 | l.sort() 42 | 43 | comb = defaultdict(lambda : 0) 44 | 45 | comb[dev] = 1 46 | 47 | for v in l[::-1]: 48 | comb[v] = comb[v+1] + comb[v+2] + comb[v+3] 49 | #print(v , comb[v]) 50 | 51 | print("Part 2 answer :", comb[0]) 52 | 53 | if __name__ == "__main__": 54 | 55 | part1() 56 | part2() 57 | -------------------------------------------------------------------------------- /2020/day15/code.py: -------------------------------------------------------------------------------- 1 | import time,os 2 | from collections import defaultdict 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 9 | return ret 10 | return wrapper_method 11 | 12 | @profiler 13 | def part1(): 14 | 15 | input = list(map(int, open('input.txt', 'r').read().split(','))) 16 | 17 | for _ in range(2020): 18 | if input.count(input[-1]) == 1 : 19 | input.append(0) 20 | else : 21 | idx = [i for i,num in enumerate(input) if num == input[-1]] 22 | input.append(idx[-1] - idx[-2]) 23 | 24 | print(input[-1]) 25 | 26 | 27 | @profiler 28 | def part2(): 29 | 30 | input = list(map(int, open('input.txt', 'r').read().split(','))) 31 | 32 | age = defaultdict(list) 33 | 34 | for i in range(30000000): 35 | if len(input) == 0 : 36 | if len(age[mem]) < 2 : 37 | next = 0 38 | else : 39 | next = age[mem][-1] - age[mem][-2] 40 | age[next].append(i) 41 | mem = next 42 | 43 | else : 44 | mem = input.pop(0) 45 | age[mem].append(i) 46 | 47 | 48 | print(age.keys()) 49 | print(mem) 50 | 51 | @profiler 52 | def part2_list(): 53 | 54 | input = list(map(int, open('input.txt', 'r').read().split(','))) 55 | 56 | for _ in range(30000000): 57 | if input.count(input[-1]) == 1 : 58 | input.append(0) 59 | else : 60 | idx = [i for i,num in enumerate(input) if num == input[-1]] 61 | input.append(idx[-1] - idx[-2]) 62 | 63 | print(input[30000000-1]) 64 | if __name__ == "__main__": 65 | 66 | part1() 67 | part2() 68 | #part2_list() 69 | -------------------------------------------------------------------------------- /2020/day20/monster.txt: -------------------------------------------------------------------------------- 1 | # 2 | # ## ## ### 3 | # # # # # # -------------------------------------------------------------------------------- /2020/day25/code.py: -------------------------------------------------------------------------------- 1 | import time,os,re 2 | from copy import deepcopy 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 9 | return ret 10 | return wrapper_method 11 | 12 | def get_loop_size(subject_num , pub_key): 13 | loop_size = 0 14 | val = 1 15 | while val != pub_key: 16 | loop_size += 1 17 | val = (val * subject_num) % 20201227 18 | return loop_size 19 | 20 | def get_encryption_key(loop_size,subject_num): 21 | return pow(subject_num , loop_size , 20201227) 22 | 23 | @profiler 24 | def part1(): 25 | card_pub_key = 15335876 26 | door_pub_key = 15086442 27 | 28 | door_loop_size = get_loop_size(7,door_pub_key) 29 | card_loop_size = get_loop_size(7,card_pub_key) 30 | 31 | encryp_door = get_encryption_key(door_loop_size , card_pub_key) 32 | encryp_card = get_encryption_key(card_loop_size , door_pub_key) 33 | 34 | assert encryp_card == encryp_door 35 | print(encryp_card) 36 | 37 | if __name__ == "__main__": 38 | 39 | part1() -------------------------------------------------------------------------------- /2020/init2020.py: -------------------------------------------------------------------------------- 1 | import os 2 | 3 | 4 | for i in range(25): 5 | dir = "day" + "{:02d}".format(i+1) 6 | if not os.path.exists(dir): 7 | os.mkdir(dir) 8 | open(dir + "/input.txt", "w").close() 9 | f_code = open(dir + '/code.py' , 'w') 10 | 11 | f_code.write('''import time,os 12 | 13 | def profiler(method): 14 | def wrapper_method(*arg, **kw): 15 | t = time.time() 16 | method(*arg, **kw) 17 | print('Method ' + method.__name__ +' took : ' + "{:2.5f}".format(time.time()-t) + ' sec') 18 | return wrapper_method 19 | 20 | @profiler 21 | def part1(): 22 | 23 | with open('input.txt', 'r') as f_in: 24 | pass 25 | 26 | 27 | @profiler 28 | def part2(): 29 | with open('input.txt', 'r') as f_in: 30 | pass 31 | 32 | if __name__ == "__main__": 33 | 34 | 35 | part1() 36 | part2() 37 | 38 | 39 | ''' 40 | ) 41 | 42 | f_code.close() -------------------------------------------------------------------------------- /2021/.gitignore: -------------------------------------------------------------------------------- 1 | Cargo.lock 2 | target/ -------------------------------------------------------------------------------- /2021/Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "advent_of_code" 3 | version = "0.1.0" 4 | edition = "2021" 5 | 6 | [dependencies] 7 | regex = "1" 8 | 9 | [[bin]] 10 | name="day01" 11 | path="day01/main.rs" 12 | 13 | [[bin]] 14 | name="day02" 15 | path="day02/main.rs" 16 | 17 | [[bin]] 18 | name="day03" 19 | path="day03/main.rs" 20 | 21 | [[bin]] 22 | name="day04" 23 | path="day04/main.rs" 24 | 25 | [[bin]] 26 | name="day05" 27 | path="day05/main.rs" 28 | 29 | [[bin]] 30 | name="day06" 31 | path="day06/main.rs" 32 | 33 | [[bin]] 34 | name="day07" 35 | path="day07/main.rs" 36 | 37 | [[bin]] 38 | name="day08" 39 | path="day08/main.rs" 40 | 41 | [[bin]] 42 | name="day09" 43 | path="day09/main.rs" 44 | 45 | [[bin]] 46 | name="day10" 47 | path="day10/main.rs" 48 | 49 | [[bin]] 50 | name="day11" 51 | path="day11/main.rs" 52 | 53 | [[bin]] 54 | name="day12" 55 | path="day12/main.rs" 56 | 57 | [[bin]] 58 | name="day13" 59 | path="day13/main.rs" 60 | 61 | [[bin]] 62 | name="day14" 63 | path="day14/main.rs" 64 | 65 | [[bin]] 66 | name="day15" 67 | path="day15/main.rs" 68 | 69 | [[bin]] 70 | name="day16" 71 | path="day16/main.rs" 72 | 73 | [[bin]] 74 | name="day17" 75 | path="day17/main.rs" 76 | 77 | [[bin]] 78 | name="day18" 79 | path="day18/main.rs" 80 | 81 | [[bin]] 82 | name="day19" 83 | path="day19/main.rs" 84 | 85 | [[bin]] 86 | name="day20" 87 | path="day20/main.rs" 88 | 89 | [[bin]] 90 | name="day21" 91 | path="day21/main.rs" 92 | 93 | [[bin]] 94 | name="day22" 95 | path="day22/main.rs" 96 | 97 | [[bin]] 98 | name="day23" 99 | path="day23/main.rs" 100 | 101 | [[bin]] 102 | name="day25" 103 | path="day25/main.rs" -------------------------------------------------------------------------------- /2021/day01/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import os 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | ret = method(*arg, **kw) 9 | print('Method ' + method.__name__ + ' took : ' + 10 | "{:2.5f}".format(time.time()-t) + ' sec') 11 | return ret 12 | return wrapper_method 13 | 14 | 15 | @profiler 16 | def part1(): 17 | l = [int(l) for l in open('input.txt')] 18 | 19 | cnt = sum([l[i] > l[i-1] for i in range(1, len(l))]) 20 | 21 | print("part 1 ", cnt) 22 | 23 | 24 | @profiler 25 | def part2(): 26 | l = [int(l) for l in open('input.txt')] 27 | 28 | cnt2 = sum([l[i+1] > l[i-2] for i in range(2, len(l) - 1)]) 29 | 30 | print("part 2 ", cnt2) 31 | 32 | 33 | if __name__ == "__main__": 34 | 35 | part1() 36 | part2() 37 | -------------------------------------------------------------------------------- /2021/day01/main.rs: -------------------------------------------------------------------------------- 1 | use std::fs; 2 | use std::time; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | let nums: Vec = fs::read_to_string("day01/input.txt") 14 | .unwrap() 15 | .lines() 16 | .map(|v| v.parse::().unwrap()) 17 | .collect(); 18 | 19 | let mut cnt: u16 = 0; 20 | for i in 1..nums.len() { 21 | if nums[i] > nums[i - 1] { 22 | cnt += 1; 23 | } 24 | } 25 | 26 | println!("part 1 : {}", cnt); 27 | } 28 | 29 | fn part_2() { 30 | let nums: Vec = fs::read_to_string("day01/input.txt") 31 | .unwrap() 32 | .lines() 33 | .map(|v| v.parse::().unwrap()) 34 | .collect(); 35 | 36 | let mut cnt: u16 = 0; 37 | for i in 2..nums.len() - 1 { 38 | if nums[i + 1] > nums[i - 2] { 39 | cnt += 1; 40 | } 41 | } 42 | 43 | println!("part 2 : {}", cnt); 44 | } 45 | 46 | fn main() { 47 | bench(part_1); 48 | bench(part_2); 49 | } 50 | -------------------------------------------------------------------------------- /2021/day02/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | import re 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | ret = method(*arg, **kw) 9 | print('Method ' + method.__name__ + ' took : ' + 10 | "{:2.5f}".format(time.time()-t) + ' sec') 11 | return ret 12 | return wrapper_method 13 | 14 | 15 | @profiler 16 | def part1(): 17 | 18 | pos = 0 19 | 20 | for l in open('input.txt'): 21 | ds = int(re.findall(r'\d+', l)[0]) 22 | if "up" in l: 23 | pos -= ds * 1j 24 | elif "down" in l: 25 | pos += ds * 1j 26 | elif "forward" in l: 27 | pos += ds 28 | 29 | print("part 1 :", int(pos.real * pos.imag)) 30 | 31 | 32 | @profiler 33 | def part2(): 34 | 35 | pos = 0 36 | aim = 0 37 | 38 | for l in open('input.txt'): 39 | ds = int(re.findall(r'\d+', l)[0]) 40 | if "up" in l: 41 | aim -= ds 42 | elif "down" in l: 43 | aim += ds 44 | elif "forward" in l: 45 | pos += ds 46 | pos += (aim * ds * 1j) 47 | 48 | print("part 2 :", int(pos.real * pos.imag)) 49 | 50 | 51 | if __name__ == "__main__": 52 | 53 | part1() 54 | part2() 55 | -------------------------------------------------------------------------------- /2021/day02/main.rs: -------------------------------------------------------------------------------- 1 | use std::fs; 2 | use std::time; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | struct Postion { 13 | x: i32, 14 | y: i32, 15 | } 16 | 17 | fn part_1() { 18 | let mut pos = Postion { x: 0, y: 0 }; 19 | 20 | for l in fs::read_to_string("day02/input.txt").unwrap().lines() { 21 | let p: Vec<&str> = l.split(" ").collect(); 22 | if p[0] == "up" { 23 | pos.y -= p[1].parse::().unwrap(); 24 | } else if p[0] == "down" { 25 | pos.y += p[1].parse::().unwrap(); 26 | } else if p[0] == "forward" { 27 | pos.x += p[1].parse::().unwrap(); 28 | } 29 | } 30 | 31 | println!("{:?}", pos.x * pos.y); 32 | } 33 | 34 | fn part_2() { 35 | let mut pos = Postion { x: 0, y: 0 }; 36 | let mut aim: i32 = 0; 37 | 38 | for l in fs::read_to_string("day02/input.txt").unwrap().lines() { 39 | let p: Vec<&str> = l.split(" ").collect(); 40 | let ds = p[1].parse::().unwrap(); 41 | if p[0] == "up" { 42 | aim -= ds; 43 | } else if p[0] == "down" { 44 | aim += ds; 45 | } else if p[0] == "forward" { 46 | pos.x += ds; 47 | pos.y += ds * aim; 48 | } 49 | } 50 | 51 | println!("{:?}", pos.x * pos.y); 52 | } 53 | 54 | fn main() { 55 | bench(part_1); 56 | bench(part_2); 57 | } 58 | -------------------------------------------------------------------------------- /2021/day03/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | from collections import defaultdict 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | ret = method(*arg, **kw) 9 | print('Method ' + method.__name__ + ' took : ' + 10 | "{:2.5f}".format(time.time()-t) + ' sec') 11 | return ret 12 | return wrapper_method 13 | 14 | 15 | @profiler 16 | def part1(): 17 | nums = [l.strip() for l in open("input.txt")] 18 | 19 | gamma = list(nums[0]) 20 | 21 | for bit in range(len(nums[0])): 22 | bits = [l[bit] for l in nums] 23 | 24 | gamma[bit] = str(int(bits.count('1') > bits.count('0') * 1)) 25 | 26 | epsilon = int(''.join(gamma).replace( 27 | '0', 'x').replace('1', '0').replace('x', '1'), 2) 28 | gamma = int(''.join(gamma), 2) 29 | 30 | print("part 1 : ", gamma * epsilon) 31 | 32 | 33 | @profiler 34 | def part2(): 35 | 36 | nums_oxy = [l.strip() for l in open("input.txt")] 37 | nums_car = nums_oxy.copy() 38 | 39 | for bit in range(len(nums_oxy[0])): 40 | 41 | bits_oxy = [l[bit] for l in nums_oxy] 42 | 43 | keep = '1' if bits_oxy.count('1') >= bits_oxy.count('0') else '0' 44 | 45 | nums_oxy = list(filter(lambda x: x[bit] == keep, nums_oxy)) 46 | 47 | if len(nums_oxy) == 1: 48 | break 49 | 50 | for bit in range(len(nums_car[0])): 51 | 52 | bits_car = [l[bit] for l in nums_car] 53 | 54 | keep = '0' if bits_car.count('1') >= bits_car.count('0') else '1' 55 | 56 | nums_car = list(filter(lambda x: x[bit] == keep, nums_car)) 57 | 58 | if len(nums_car) == 1: 59 | break 60 | 61 | print("part 2 : ", int(nums_oxy[0], 2) * int(nums_car[0], 2)) 62 | 63 | 64 | if __name__ == "__main__": 65 | 66 | part1() 67 | part2() 68 | -------------------------------------------------------------------------------- /2021/day04/main.rs: -------------------------------------------------------------------------------- 1 | use std::fs::*; 2 | use std::io::Read; 3 | use std::time; 4 | 5 | fn bench(f: fn()) { 6 | let t0 = time::Instant::now(); 7 | let ret = f(); 8 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 9 | 10 | ret 11 | } 12 | 13 | fn part_1() { 14 | let mut buf = String::new(); 15 | File::open("day04/input.txt") 16 | .unwrap() 17 | .read_to_string(&mut buf) 18 | .unwrap(); 19 | 20 | let ls: Vec<_> = buf.split("\n\n").collect(); 21 | 22 | let nums: Vec<_> = ls[0] 23 | .split(',') 24 | .map(|x| x.parse::().unwrap()) 25 | .collect(); 26 | 27 | let mut boards: Vec>> = Vec::new(); 28 | 29 | for board in ls.iter().skip(1) { 30 | let mut b: Vec> = Vec::new(); 31 | for l in board.split('\n') { 32 | b.push( 33 | l.split_whitespace() 34 | .map(|n| n.parse::().unwrap()) 35 | .collect(), 36 | ); 37 | } 38 | boards.push(b); 39 | } 40 | for num in nums{ 41 | for board in &boards{ 42 | for l in board{ 43 | if l.contains(&num){ 44 | 45 | } 46 | } 47 | } 48 | } 49 | } 50 | 51 | 52 | fn part_2() {} 53 | 54 | fn main() { 55 | bench(part_1); 56 | bench(part_2); 57 | } 58 | -------------------------------------------------------------------------------- /2021/day06/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(time.time()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | input = [int(i) for i in open("day06/input.txt").read().split(',')] 17 | 18 | for _ in range(80): 19 | tmp = [] 20 | for i in input: 21 | if i == 0: 22 | tmp.append(8) 23 | tmp.append(6) 24 | else: 25 | tmp.append(i-1) 26 | 27 | input = tmp 28 | 29 | print(len(tmp)) 30 | 31 | 32 | @profiler 33 | def part2(): 34 | 35 | input = [int(i) for i in open("day06/input.txt").read().split(',')] 36 | 37 | ages = {i: 0 for i in range(9)} 38 | 39 | for age in input: 40 | ages[age] += 1 41 | 42 | for _ in range(256): 43 | new_ages = {i: 0 for i in range(9)} 44 | for age in ages: 45 | if age == 0: 46 | new_ages[8] += ages[0] 47 | new_ages[6] += ages[0] 48 | else: 49 | new_ages[age-1] += ages[age] 50 | 51 | ages = new_ages 52 | 53 | print(sum(ages.values())) 54 | 55 | 56 | if __name__ == "__main__": 57 | 58 | part1() 59 | part2() 60 | -------------------------------------------------------------------------------- /2021/day07/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(time.time()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | input = list(map(int, open("day07/input.txt").read().split(','))) 17 | 18 | p1 = min([sum(map(lambda x: abs(x-i), input)) for i in range(max(input))]) 19 | 20 | print("part 1 : ", p1) 21 | 22 | 23 | def get_fuel(dist): 24 | return dist * (dist + 1) // 2 25 | 26 | 27 | @profiler 28 | def part2(): 29 | input = list(map(int, open("day07/input.txt").read().split(','))) 30 | 31 | p2 = min([sum(map(lambda x: get_fuel(abs(x-i)), input)) for i in range(max(input))]) 32 | 33 | print("part 2 : ", p2) 34 | 35 | 36 | if __name__ == "__main__": 37 | 38 | part1() 39 | part2() 40 | -------------------------------------------------------------------------------- /2021/day07/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | 3 | fn bench(f: fn()) { 4 | let t0 = time::Instant::now(); 5 | let ret = f(); 6 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 7 | 8 | ret 9 | } 10 | 11 | fn get_fuel_p1(input: &[i32], i: i32) -> i32 { 12 | input 13 | .iter() 14 | .map(|x| (x - i).abs()) 15 | .collect::>() 16 | .iter() 17 | .sum() 18 | } 19 | 20 | fn part_1() { 21 | let input = include_str!("input.txt") 22 | .split(',') 23 | .map(|x| x.parse::().unwrap()) 24 | .collect::>(); 25 | 26 | let p1 = *(0..=*input.iter().max().unwrap()) 27 | .collect::>() 28 | .iter() 29 | .map(|v| get_fuel_p1(&input, v.clone())) 30 | .collect::>() 31 | .iter() 32 | .min() 33 | .unwrap(); 34 | 35 | println!("part 1 : {:?}", p1); 36 | } 37 | 38 | fn get_fuel_p2(input: &[i32], i: i32) -> i32 { 39 | input 40 | .iter() 41 | .map(|x| { 42 | let dist = (x - i).abs(); 43 | dist * (dist + 1) / 2 44 | }) 45 | .collect::>() 46 | .iter() 47 | .sum() 48 | } 49 | 50 | fn part_2() { 51 | let input = include_str!("input.txt") 52 | .split(',') 53 | .map(|x| x.parse::().unwrap()) 54 | .collect::>(); 55 | 56 | let p2 = *(0..=*input.iter().max().unwrap()) 57 | .collect::>() 58 | .iter() 59 | .map(|v| get_fuel_p2(&input, v.clone())) 60 | .collect::>() 61 | .iter() 62 | .min() 63 | .unwrap(); 64 | 65 | println!("part 2 : {:?}", p2); 66 | } 67 | 68 | fn main() { 69 | bench(part_1); 70 | bench(part_2); 71 | } 72 | -------------------------------------------------------------------------------- /2021/day10/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(time.time()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | total = 0 17 | 18 | illegal = {')' : 3 , ']' : 57 , '}' : 1197 , '>' : 25137} 19 | 20 | for o in open("day10/input.txt"): 21 | l = o.strip() 22 | while l.count('{}') > 0 or l.count('[]') > 0 or l.count("<>") > 0 or l.count("()") > 0: 23 | l = l.replace("{}" , "").replace("<>","").replace("[]","").replace("()","") 24 | 25 | 26 | p = [l.index(i) for i in illegal if i in l] 27 | 28 | if len(p) > 0: 29 | total += illegal[l[min(p)]] 30 | 31 | print(total) 32 | 33 | 34 | @profiler 35 | def part2(): 36 | 37 | prize = {')' : 1 , ']' : 2 , '}' : 3 , '>' : 4} 38 | comp = {'{' : '}' , '(' : ')' , '[' : ']' , '<' : '>'} 39 | 40 | scores = [] 41 | for o in open("day10/input.txt"): 42 | l = o.strip() 43 | while l.count('{}') > 0 or l.count('[]') > 0 or l.count("<>") > 0 or l.count("()") > 0: 44 | l = l.replace("{}" , "").replace("<>","").replace("[]","").replace("()","") 45 | 46 | 47 | p = [l.index(i) for i in prize if i in l] 48 | 49 | if len(p) == 0: 50 | local_tmp = 0 51 | for i in l[::-1]: 52 | local_tmp *= 5 53 | local_tmp += prize[comp[i]] 54 | 55 | scores.append(local_tmp) 56 | 57 | scores.sort() 58 | print(scores[len(scores) //2]) 59 | 60 | 61 | if __name__ == "__main__": 62 | 63 | part1() 64 | part2() 65 | -------------------------------------------------------------------------------- /2021/day10/main.rs: -------------------------------------------------------------------------------- 1 | use std::fs; 2 | use std::time; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | for _l in fs::read_to_string("day10/input.txt").unwrap().lines() {} 14 | } 15 | 16 | fn part_2() {} 17 | 18 | fn main() { 19 | bench(part_1); 20 | bench(part_2); 21 | } 22 | -------------------------------------------------------------------------------- /2021/day13/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print( 9 | "Method " 10 | + method.__name__ 11 | + " took : " 12 | + "{:2.5f}".format(time.time() - t) 13 | + " sec" 14 | ) 15 | return ret 16 | 17 | return wrapper_method 18 | 19 | 20 | def fold_grid(dots, fold): 21 | 22 | axe, loc = fold 23 | if axe == "x": 24 | return {(loc - (p[0] - loc), p[1]) if p[0] > loc else p for p in dots} 25 | else: 26 | return {(p[0], loc - (p[1] - loc)) if p[1] > loc else p for p in dots} 27 | 28 | 29 | @profiler 30 | def part1(): 31 | dots = set() 32 | fold = [] 33 | for l in open("day13/input.txt"): 34 | if "," in l: 35 | dots.add(tuple(map(int, l.strip().split(",")))) 36 | elif "fold" in l: 37 | p = l.split("=") 38 | fold.append(tuple((p[0][-1], int(p[1])))) 39 | 40 | dots = fold_grid(dots, fold[0]) 41 | 42 | print(len(dots)) 43 | 44 | 45 | @profiler 46 | def part2(): 47 | dots = set() 48 | fold = [] 49 | for l in open("day13/input.txt"): 50 | if "," in l: 51 | dots.add(tuple(map(int, l.strip().split(",")))) 52 | elif "fold" in l: 53 | p = l.split("=") 54 | fold.append(tuple((p[0][-1], int(p[1])))) 55 | 56 | for f in fold: 57 | dots = fold_grid(dots, f) 58 | 59 | max_x = max([p[0] for p in dots]) 60 | max_y = max([p[1] for p in dots]) 61 | 62 | for y in range(max_y + 1): 63 | for x in range(max_x + 1): 64 | if (x, y) in dots: 65 | print("#", end="") 66 | else: 67 | print(" ", end="") 68 | print() 69 | 70 | 71 | if __name__ == "__main__": 72 | 73 | part1() 74 | part2() 75 | -------------------------------------------------------------------------------- /2021/day16/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | 3 | fn bench(f: fn()) { 4 | let t0 = time::Instant::now(); 5 | let ret = f(); 6 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 7 | 8 | ret 9 | } 10 | 11 | fn part_1() { 12 | for _l in include_str!("input.txt") {} 13 | } 14 | 15 | fn part_2() {} 16 | 17 | fn main() { 18 | bench(part_1); 19 | bench(part_2); 20 | } 21 | -------------------------------------------------------------------------------- /2021/day18/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | 3 | fn bench(f: fn()) { 4 | let t0 = time::Instant::now(); 5 | let ret = f(); 6 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 7 | 8 | ret 9 | } 10 | 11 | fn part_1() { 12 | include_str!("input.txt"); 13 | } 14 | 15 | fn part_2() {} 16 | 17 | fn main() { 18 | bench(part_1); 19 | bench(part_2); 20 | } 21 | -------------------------------------------------------------------------------- /2021/day20/code.py: -------------------------------------------------------------------------------- 1 | from os import XATTR_REPLACE 2 | import time 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = time.time() 8 | ret = method(*arg, **kw) 9 | print( 10 | "Method " 11 | + method.__name__ 12 | + " took : " 13 | + "{:2.5f}".format(time.time() - t) 14 | + " sec" 15 | ) 16 | return ret 17 | 18 | return wrapper_method 19 | 20 | def sim_cycles(cycles): 21 | 22 | assert(cycles%2 == 0) 23 | 24 | p = open("day20/input.txt").read().split("\n\n") 25 | 26 | algo = p[0].replace("\n", "") 27 | i = p[1].split("\n") 28 | 29 | lit_pix = set() 30 | for y, l in enumerate(i): 31 | for x, c in enumerate(l): 32 | if c == "#": 33 | lit_pix.add((x, y)) 34 | 35 | for iter in range(cycles): 36 | new_pix = set() 37 | 38 | xs = [p[0] for p in lit_pix] 39 | x_l , x_u = min(xs) , max(xs) 40 | 41 | ys = [p[1] for p in lit_pix] 42 | y_l , y_u = min(ys) , max(ys) 43 | 44 | for x in range(x_l - 1, x_u + 2): 45 | for y in range(y_l - 1, y_u + 2): 46 | idx = "" 47 | for t in range(9): 48 | nx = x + t % 3 - 1 49 | ny = y + t // 3 - 1 50 | if x_l <= nx <= x_u and y_l <= ny <= y_u : 51 | idx += '1' if (nx,ny) in lit_pix else '0' 52 | else : 53 | idx += '1' if iter%2 == 1 else '0' 54 | 55 | if algo[int(idx, 2)] == "#": 56 | new_pix.add((x, y)) 57 | lit_pix = new_pix 58 | 59 | return len(lit_pix) 60 | 61 | @profiler 62 | def part1(): 63 | print(sim_cycles(2)) 64 | 65 | 66 | @profiler 67 | def part2(): 68 | print(sim_cycles(50)) 69 | 70 | if __name__ == "__main__": 71 | 72 | part1() 73 | part2() 74 | -------------------------------------------------------------------------------- /2021/day24/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | 3 | fn bench(f: fn()) { 4 | let t0 = time::Instant::now(); 5 | let ret = f(); 6 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 7 | 8 | ret 9 | } 10 | 11 | fn part_1() { 12 | include_str!("input.txt"); 13 | } 14 | 15 | fn part_2() {} 16 | 17 | fn main() { 18 | bench(part_1); 19 | bench(part_2); 20 | } 21 | -------------------------------------------------------------------------------- /2021/day25/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print( 9 | "Method " 10 | + method.__name__ 11 | + " took : " 12 | + "{:2.5f}".format(time.time() - t) 13 | + " sec" 14 | ) 15 | return ret 16 | 17 | return wrapper_method 18 | 19 | 20 | @profiler 21 | def part1(): 22 | grid = [list(l.strip()) for l in open("day25/input.txt")] 23 | 24 | east = set() 25 | south = set() 26 | 27 | max_x = len(grid[0]) 28 | max_y = len(grid) 29 | 30 | for y, l in enumerate(grid): 31 | for x, c in enumerate(l): 32 | if c == ">": 33 | east.add((x, y)) 34 | elif c == "v": 35 | south.add((x, y)) 36 | 37 | cnt = 0 38 | while True: 39 | new_east = set() 40 | new_south = set() 41 | 42 | for e in east: 43 | n_p = ((e[0] + 1) % max_x, e[1]) 44 | if n_p not in east and n_p not in south: 45 | new_east.add(n_p) 46 | else: 47 | new_east.add(e) 48 | 49 | for s in south: 50 | n_p = (s[0], (s[1] + 1) % max_y) 51 | if n_p not in south and n_p not in new_east: 52 | new_south.add(n_p) 53 | else: 54 | new_south.add(s) 55 | 56 | cnt += 1 57 | 58 | if new_south == south and east == new_east: 59 | break 60 | south = new_south 61 | east = new_east 62 | 63 | print(cnt) 64 | 65 | 66 | if __name__ == "__main__": 67 | 68 | part1() 69 | -------------------------------------------------------------------------------- /2021/day25/main.rs: -------------------------------------------------------------------------------- 1 | use std::collections::HashSet; 2 | use std::time; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | let mut east: HashSet<(u8, u8)> = HashSet::new(); 14 | let mut south: HashSet<(u8, u8)> = HashSet::new(); 15 | let mut max_x: u8 = 0; 16 | let mut max_y: u8 = 0; 17 | 18 | for (y, l) in include_str!("input.txt").split("\n").enumerate() { 19 | max_y = y as u8 + 1; 20 | max_x = l.len() as u8; 21 | for (x, c) in l.chars().enumerate() { 22 | if c == 'v' { 23 | south.insert((x as u8, y as u8)); 24 | } else if c == '>' { 25 | east.insert((x as u8, y as u8)); 26 | } 27 | } 28 | } 29 | 30 | let mut cnt: u16 = 0; 31 | loop { 32 | let mut new_east: HashSet<(u8, u8)> = HashSet::new(); 33 | let mut new_south: HashSet<(u8, u8)> = HashSet::new(); 34 | 35 | for e in &east { 36 | let n_p = ((e.0 + 1) % max_x, e.1); 37 | if !east.contains(&n_p) && !south.contains(&n_p) { 38 | new_east.insert(n_p); 39 | } else { 40 | new_east.insert(*e); 41 | } 42 | } 43 | 44 | for s in &south { 45 | let n_p = (s.0, (s.1 + 1) % max_y); 46 | if !south.contains(&n_p) && !new_east.contains(&n_p) { 47 | new_south.insert(n_p); 48 | } else { 49 | new_south.insert(*s); 50 | } 51 | } 52 | 53 | cnt += 1; 54 | if new_east.eq(&east) && south.eq(&new_south) { 55 | break; 56 | } 57 | 58 | south = new_south; 59 | east = new_east; 60 | } 61 | 62 | println!("{}", cnt); 63 | } 64 | 65 | fn main() { 66 | bench(part_1); 67 | } 68 | -------------------------------------------------------------------------------- /2021/template/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(time.time()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | pass 17 | 18 | 19 | @profiler 20 | def part2(): 21 | pass 22 | 23 | 24 | if __name__ == "__main__": 25 | 26 | part1() 27 | part2() 28 | -------------------------------------------------------------------------------- /2021/template/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | 3 | fn bench(f: fn()) { 4 | let t0 = time::Instant::now(); 5 | let ret = f(); 6 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 7 | 8 | ret 9 | } 10 | 11 | fn part_1() { 12 | include_str!("input.txt"); 13 | } 14 | 15 | fn part_2() {} 16 | 17 | fn main() { 18 | bench(part_1); 19 | bench(part_2); 20 | } 21 | -------------------------------------------------------------------------------- /2022/.gitignore: -------------------------------------------------------------------------------- 1 | target/* 2 | Cargo.lock 3 | *.pyc -------------------------------------------------------------------------------- /2022/Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "advent_of_code" 3 | version = "0.1.0" 4 | edition = "2021" 5 | 6 | [dependencies] 7 | regex = "1" 8 | json = "*" 9 | serde_json = "1.0.89" 10 | itertools = "0.10" 11 | 12 | 13 | [[bin]] 14 | name="day01" 15 | path="day01/main.rs" 16 | 17 | [[bin]] 18 | name="day02" 19 | path="day02/main.rs" 20 | 21 | [[bin]] 22 | name="day03" 23 | path="day03/main.rs" 24 | 25 | [[bin]] 26 | name="day04" 27 | path="day04/main.rs" 28 | 29 | [[bin]] 30 | name="day05" 31 | path="day05/main.rs" 32 | 33 | [[bin]] 34 | name="day06" 35 | path="day06/main.rs" 36 | 37 | [[bin]] 38 | name="day07" 39 | path="day07/main.rs" 40 | 41 | [[bin]] 42 | name="day08" 43 | path="day08/main.rs" 44 | 45 | [[bin]] 46 | name="day09" 47 | path="day09/main.rs" 48 | 49 | [[bin]] 50 | name="day10" 51 | path="day10/main.rs" 52 | 53 | [[bin]] 54 | name="day11" 55 | path="day11/main.rs" 56 | 57 | [[bin]] 58 | name="day12" 59 | path="day12/main.rs" 60 | 61 | [[bin]] 62 | name="day13" 63 | path="day13/main.rs" 64 | 65 | [[bin]] 66 | name="day14" 67 | path="day14/main.rs" 68 | 69 | [[bin]] 70 | name="day15" 71 | path="day15/main.rs" 72 | 73 | [[bin]] 74 | name="day18" 75 | path="day18/main.rs" 76 | 77 | [[bin]] 78 | name="day19" 79 | path="day19/main.rs" 80 | 81 | [[bin]] 82 | name="day20" 83 | path="day20/main.rs" 84 | 85 | [[bin]] 86 | name="day21" 87 | path="day21/main.rs" 88 | 89 | [[bin]] 90 | name="day22" 91 | path="day22/main.rs" 92 | 93 | [[bin]] 94 | name="day23" 95 | path="day23/main.rs" 96 | 97 | [[bin]] 98 | name="day24" 99 | path="day24/main.rs" 100 | 101 | [[bin]] 102 | name="day25" 103 | path="day25/main.rs" -------------------------------------------------------------------------------- /2022/day01/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(time.time()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | cals = [sum([int(c) for c in l.split()]) 17 | for l in open("input.txt").read().split("\n\n")] 18 | print(max(cals)) 19 | 20 | 21 | @profiler 22 | def part2(): 23 | cals = [sum([int(c) for c in l.split()]) 24 | for l in open("input.txt").read().split("\n\n")] 25 | cals.sort() 26 | print(sum(cals[-3:])) 27 | 28 | 29 | if __name__ == "__main__": 30 | 31 | part1() 32 | part2() 33 | -------------------------------------------------------------------------------- /2022/day01/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | 3 | fn bench(f: fn()) { 4 | let t0 = time::Instant::now(); 5 | let ret = f(); 6 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 7 | 8 | ret 9 | } 10 | 11 | fn part_1() { 12 | let mut cals : Vec =Vec::new(); 13 | for l in include_str!("input.txt").split("\n\n"){ 14 | let temp = l.split("\n").map(|x| x.parse::().unwrap()).sum(); 15 | cals.push(temp); 16 | } 17 | cals.sort(); 18 | 19 | println!("{}" , cals.iter().last().unwrap()); 20 | } 21 | 22 | fn part_2() { 23 | let mut cals : Vec =Vec::new(); 24 | for l in include_str!("input.txt").split("\n\n"){ 25 | let temp = l.split("\n").map(|x| x.parse::().unwrap()).sum(); 26 | cals.push(temp); 27 | } 28 | cals.sort(); 29 | 30 | println!("{}" , cals.iter().rev().take(3).sum::()); 31 | } 32 | 33 | fn main() { 34 | bench(part_1); 35 | bench(part_2); 36 | } 37 | -------------------------------------------------------------------------------- /2022/day02/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | 3 | from collections import Counter, defaultdict 4 | 5 | 6 | def profiler(method): 7 | def wrapper_method(*arg, **kw): 8 | t = time.time() 9 | ret = method(*arg, **kw) 10 | print('Method ' + method.__name__ + ' took : ' + 11 | "{:2.5f}".format(time.time()-t) + ' sec') 12 | return ret 13 | return wrapper_method 14 | 15 | 16 | @profiler 17 | def part1(): 18 | freq = Counter(open("input.txt").read().splitlines()) 19 | 20 | score = 0 21 | for g in freq: 22 | hands = g.split() 23 | 24 | h0 = ord(hands[0]) - ord('A') 25 | h1 = ord(hands[1]) - ord('X') 26 | 27 | # game score = value of hand(R1,P2,S3) + 3*(L0,T1,W2) 28 | g_score = (h1 + 1) + 3 * ((h1 - h0 + 1) % 3) 29 | score += g_score * freq[g] 30 | 31 | print(score) 32 | 33 | 34 | @profiler 35 | def part2(): 36 | freq = Counter(open("input.txt").read().splitlines()) 37 | 38 | score = 0 39 | for g in freq: 40 | hands = g.split() 41 | 42 | h0 = ord(hands[0]) - ord('A') 43 | h1 = ord(hands[1]) - ord('X') 44 | 45 | g_score = h1 * 3 + (h0 + h1 - 1) % 3 + 1 46 | 47 | score += g_score * freq[g] 48 | 49 | print(score) 50 | 51 | 52 | if __name__ == "__main__": 53 | 54 | part1() 55 | part2() 56 | -------------------------------------------------------------------------------- /2022/day02/main.rs: -------------------------------------------------------------------------------- 1 | use std::collections::HashMap; 2 | use std::time; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | let mut freq: HashMap<&str, u16> = HashMap::new(); 14 | for l in include_str!("input.txt").split("\n") { 15 | *freq.entry(l).or_default() += 1; 16 | } 17 | 18 | let mut score: u16 = 0; 19 | for k in freq { 20 | let hands: Vec<_> = k.0.split(' ').collect(); 21 | 22 | let h0 = hands[0].chars().next().unwrap() as u16 - 'A' as u16; 23 | let h1 = hands[1].chars().next().unwrap() as u16 - 'X' as u16; 24 | 25 | // game score = value of hand(R1,P2,S3) + 3*(L0,T1,W2) 26 | let g_score = (h1 + 1) + (3 * (((h1 as i8 - h0 as i8) + 4) % 3)) as u16; 27 | 28 | score += (g_score as u16 * k.1) as u16; 29 | } 30 | 31 | println!("{}", score); 32 | } 33 | 34 | fn part_2() { 35 | let mut freq: HashMap<&str, u16> = HashMap::new(); 36 | for l in include_str!("input.txt").split("\n") { 37 | *freq.entry(l).or_default() += 1; 38 | } 39 | 40 | let mut score: u16 = 0; 41 | for k in freq { 42 | let hands: Vec<_> = k.0.split(' ').collect(); 43 | 44 | let h0 = hands[0].chars().next().unwrap() as u16 - 'A' as u16; 45 | let h1 = hands[1].chars().next().unwrap() as u16 - 'X' as u16; 46 | 47 | let g_score = h1 * 3 + (h0 as i8 + h1 as i8 +3 -1) as u16 % 3 + 1 ; 48 | 49 | score += g_score * k.1; 50 | } 51 | 52 | println!("{}", score); 53 | } 54 | 55 | fn main() { 56 | bench(part_1); 57 | bench(part_2); 58 | } 59 | -------------------------------------------------------------------------------- /2022/day03/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = time.time() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(time.time()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | 14 | def getvalue(c): 15 | if ord(c) < ord('a'): 16 | return ord(c) - ord('A') + 1 + 26 17 | else: 18 | return ord(c) - ord('a') + 1 19 | 20 | 21 | @profiler 22 | def part1(): 23 | total = 0 24 | 25 | for l in open("input.txt").read().splitlines(): 26 | h1 = set(l[:len(l)//2]) 27 | h2 = set(l[len(l)//2:]) 28 | 29 | total += getvalue(h1.intersection(h2).pop()) 30 | 31 | print(total) 32 | 33 | 34 | @profiler 35 | def part2(): 36 | total = 0 37 | 38 | items = open("input.txt").read().splitlines() 39 | 40 | for i in range(0, len(items), 3): 41 | h1 = set(items[i]) 42 | h2 = set(items[i+1]) 43 | h3 = set(items[i+2]) 44 | 45 | total += getvalue(h1.intersection(h2).intersection(h3).pop()) 46 | 47 | print(total) 48 | 49 | 50 | if __name__ == "__main__": 51 | 52 | part1() 53 | part2() 54 | -------------------------------------------------------------------------------- /2022/day03/main.rs: -------------------------------------------------------------------------------- 1 | use std::collections::HashSet; 2 | use std::fs::File; 3 | use std::io::{BufRead, BufReader}; 4 | use std::time; 5 | 6 | fn bench(f: fn()) { 7 | let t0 = time::Instant::now(); 8 | let ret = f(); 9 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 10 | 11 | ret 12 | } 13 | fn get_value(c: char) -> u8 { 14 | if (c as u8) < ('a' as u8) { 15 | (c as u8) - ('A' as u8) + 1 + 26 16 | } else { 17 | (c as u8) - ('a' as u8) + 1 18 | } 19 | } 20 | 21 | fn part_1() { 22 | let input = BufReader::new(File::open("day03/input.txt").unwrap()).lines(); 23 | 24 | let mut total: u16 = 0; 25 | for l in input.map(|x| x.unwrap()) { 26 | let h1: HashSet = l[..l.len() / 2].chars().collect(); 27 | let h2: HashSet = l[l.len() / 2..].chars().collect(); 28 | 29 | total += get_value(*h1.intersection(&h2).into_iter().last().unwrap()) as u16; 30 | } 31 | 32 | println!("{}", total); 33 | } 34 | 35 | fn part_2() { 36 | let input: Vec<&str> = include_str!("input.txt").split("\n").collect(); 37 | let mut total: u16 = 0; 38 | for i in (0..input.len()).step_by(3) { 39 | let h1: HashSet = input[i].chars().collect(); 40 | let h2: HashSet = input[i + 1].chars().collect(); 41 | let h3: HashSet = input[i + 2].chars().collect(); 42 | 43 | let c = h1 44 | .intersection(&h2) 45 | .map(|x| x.clone()) 46 | .collect::>() 47 | .intersection(&h3) 48 | .next() 49 | .unwrap() 50 | .clone(); 51 | 52 | total += get_value(c) as u16; 53 | } 54 | 55 | println!("{}", total); 56 | } 57 | 58 | fn main() { 59 | bench(part_1); 60 | bench(part_2); 61 | } 62 | -------------------------------------------------------------------------------- /2022/day04/code.py: -------------------------------------------------------------------------------- 1 | import time 2 | 3 | def profiler(method): 4 | def wrapper_method(*arg, **kw): 5 | t = time.time() 6 | ret = method(*arg, **kw) 7 | print('Method ' + method.__name__ + ' took : ' + 8 | "{:2.5f}".format(time.time()-t) + ' sec') 9 | return ret 10 | return wrapper_method 11 | 12 | @profiler 13 | def part1(): 14 | total = 0 15 | for l in open("input.txt"): 16 | d1, d2, d3, d4 = list(map(int, l.replace('-', ',').split(','))) 17 | if (d1 <= d3 and d2 >= d4) or (d3 <= d1 and d4 >= d2): 18 | total += 1 19 | 20 | print(total) 21 | 22 | @profiler 23 | def part2(): 24 | total = 0 25 | for l in open("input.txt"): 26 | d1, d2, d3, d4 = list(map(int, l.replace('-', ',').split(','))) 27 | if d1 <= d3 <= d2 or d1 <= d4 <= d2 or d3 <= d1 <= d4 or d3 <= d2 <= d4: 28 | total += 1 29 | 30 | print(total) 31 | 32 | if __name__ == "__main__": 33 | 34 | part1() 35 | part2() 36 | -------------------------------------------------------------------------------- /2022/day04/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | 3 | fn bench(f: fn()) { 4 | let t0 = time::Instant::now(); 5 | let ret = f(); 6 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 7 | 8 | ret 9 | } 10 | 11 | fn is_fully_contained(s: &str) -> bool { 12 | let ds: Vec<_> = s 13 | .replace("-", ",") 14 | .split(',') 15 | .map(|x| x.parse::().unwrap()) 16 | .collect(); 17 | if (ds[0] <= ds[2] && ds[1] >= ds[3]) || (ds[2] <= ds[0] && ds[3] >= ds[1]) { 18 | true 19 | } else { 20 | false 21 | } 22 | } 23 | 24 | fn part_1() { 25 | println!( 26 | "{}", 27 | include_str!("input.txt") 28 | .lines() 29 | .filter(|x| is_fully_contained(x)) 30 | .count() 31 | ); 32 | } 33 | 34 | fn is_overlapping(s: &str) -> bool { 35 | let ds: Vec<_> = s 36 | .replace("-", ",") 37 | .split(',') 38 | .map(|x| x.parse::().unwrap()) 39 | .collect(); 40 | if (ds[2] >= ds[0] && ds[2] <= ds[1]) 41 | || (ds[3] >= ds[0] && ds[3] <= ds[1]) 42 | || (ds[0] >= ds[2] && ds[0] <= ds[3]) 43 | || (ds[1] >= ds[2] && ds[1] <= ds[3]) 44 | { 45 | true 46 | } else { 47 | false 48 | } 49 | } 50 | 51 | fn part_2() { 52 | println!( 53 | "{}", 54 | include_str!("input.txt") 55 | .lines() 56 | .filter(|x| is_overlapping(x)) 57 | .count() 58 | ); 59 | } 60 | 61 | fn main() { 62 | bench(part_1); 63 | bench(part_2); 64 | } 65 | -------------------------------------------------------------------------------- /2022/day05/code.py: -------------------------------------------------------------------------------- 1 | from collections import defaultdict 2 | from time import perf_counter 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = perf_counter() 8 | ret = method(*arg, **kw) 9 | print('Method ' + method.__name__ + ' took : ' + 10 | "{:2.5f}".format(perf_counter()-t) + ' sec') 11 | return ret 12 | return wrapper_method 13 | 14 | 15 | @profiler 16 | def part1(): 17 | cargo = defaultdict(list) 18 | parts = open("input.txt").read().split("\n\n") 19 | config = parts[0].split('\n') 20 | 21 | for l in config[:-1]: 22 | for i, c in enumerate(l): 23 | if c.isalpha(): 24 | cargo[config[-1][i]].insert(0, c) 25 | 26 | for l in parts[1].split("\n"): 27 | move = list(l.replace("move", "").replace( 28 | "to", "").replace("from", "").split()) 29 | 30 | cargo[move[2]] += cargo[move[1]][-int(move[0]):][::-1] 31 | del cargo[move[1]][-int(move[0]):] 32 | 33 | print("".join([cargo[str(i)][-1] for i in range(1, 10)])) 34 | 35 | 36 | @profiler 37 | def part2(): 38 | cargo = defaultdict(list) 39 | parts = open("input.txt").read().split("\n\n") 40 | config = parts[0].split('\n') 41 | 42 | for l in config[:-1]: 43 | for i, c in enumerate(l): 44 | if c.isalpha(): 45 | cargo[config[-1][i]].insert(0, c) 46 | 47 | for l in parts[1].split("\n"): 48 | move = list(l.replace("move", "").replace( 49 | "to", "").replace("from", "").split()) 50 | 51 | cargo[move[2]] += cargo[move[1]][-int(move[0]):] 52 | del cargo[move[1]][-int(move[0]):] 53 | 54 | print("".join([cargo[str(i)][-1] for i in range(1, 10)])) 55 | 56 | 57 | if __name__ == "__main__": 58 | 59 | part1() 60 | part2() 61 | -------------------------------------------------------------------------------- /2022/day06/code.py: -------------------------------------------------------------------------------- 1 | from time import perf_counter 2 | 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = perf_counter() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(perf_counter()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | l = open("input.txt").read() 17 | target_len = 4 18 | for i in range(target_len-1, len(l)): 19 | if len(set(l[i-target_len:i])) == target_len: 20 | print(i) 21 | break 22 | 23 | 24 | @profiler 25 | def part2(): 26 | l = open("input.txt").read() 27 | target_len = 14 28 | for i in range(target_len-1, len(l)): 29 | if len(set(l[i-target_len:i])) == target_len: 30 | print(i) 31 | break 32 | 33 | if __name__ == "__main__": 34 | 35 | part1() 36 | part2() 37 | -------------------------------------------------------------------------------- /2022/day06/main.rs: -------------------------------------------------------------------------------- 1 | use std::collections::HashSet; 2 | use std::time; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | let l = include_str!("input.txt").chars().collect::>(); 14 | 15 | let target_len = 4; 16 | 17 | for i in target_len..l.len() { 18 | let message: HashSet<&char> = HashSet::from_iter(l[(i - target_len)..i].iter()); 19 | 20 | if message.len() == target_len { 21 | println!("{}", i); 22 | break; 23 | } 24 | } 25 | } 26 | 27 | fn part_2() { 28 | let l = include_str!("input.txt").chars().collect::>(); 29 | 30 | let target_len = 14; 31 | 32 | for i in target_len..l.len() { 33 | let message: HashSet<&char> = HashSet::from_iter(l[(i - target_len)..i].iter()); 34 | 35 | if message.len() == target_len { 36 | println!("{}", i); 37 | break; 38 | } 39 | } 40 | } 41 | 42 | fn main() { 43 | bench(part_1); 44 | bench(part_2); 45 | } 46 | -------------------------------------------------------------------------------- /2022/day10/code.py: -------------------------------------------------------------------------------- 1 | from time import perf_counter 2 | 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = perf_counter() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(perf_counter()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | x = 1 17 | cycle = 0 18 | strength = {} 19 | 20 | 21 | for l in open("input.txt").read().splitlines(): 22 | if "addx" in l: 23 | cycle += 1 24 | strength[cycle] = (x, x * cycle) 25 | cycle += 1 26 | strength[cycle] = (x, x * cycle) 27 | x += int(l.split(" ")[1]) 28 | else: 29 | cycle += 1 30 | strength[cycle] = (x, x * cycle) 31 | 32 | print(sum([strength[cycle][1] for cycle in [20,60,100,140,180,220]])) 33 | 34 | 35 | @profiler 36 | def part2(): 37 | x = 1 38 | cycle = 0 39 | strength = {} 40 | 41 | for l in open("input.txt").read().splitlines(): 42 | if "addx" in l: 43 | cycle += 1 44 | strength[cycle] = (x, x * cycle) 45 | cycle += 1 46 | strength[cycle] = (x, x * cycle) 47 | x += int(l.split(" ")[1]) 48 | else: 49 | cycle += 1 50 | strength[cycle] = (x, x * cycle) 51 | 52 | screen = [[' ' for x in range(40)] for y in range(6)] 53 | 54 | for cycle in strength: 55 | x = strength[cycle][0] 56 | if (cycle-1)%40 in [x-1,x,x+1]: 57 | screen[(cycle-1)//40][(cycle-1)%40] = "0" 58 | 59 | for l in screen: 60 | print("".join(l)) 61 | 62 | 63 | if __name__ == "__main__": 64 | 65 | part1() 66 | part2() 67 | -------------------------------------------------------------------------------- /2022/day17/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | use std::fs; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | fs::read_to_string("input.txt").unwrap().split("\n"); 14 | } 15 | 16 | fn part_2() { 17 | fs::read_to_string("input.txt").unwrap().split("\n"); 18 | } 19 | 20 | fn main() { 21 | bench(part_1); 22 | bench(part_2); 23 | } 24 | -------------------------------------------------------------------------------- /2022/day20/code.py: -------------------------------------------------------------------------------- 1 | from time import time as perf_counter 2 | 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = perf_counter() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(perf_counter()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | input = [int(l) for l in open("input.txt")] 17 | 18 | buffer = [(idx, i) for idx, i in enumerate(input)] 19 | 20 | for idx, i in enumerate(input): 21 | old_idx = buffer.index((idx, i)) 22 | 23 | buffer.remove((idx, i)) 24 | buffer.insert((old_idx + i + len(input) - 1) % 25 | (len(input) - 1), (-1, i)) 26 | 27 | zero_idx = buffer.index((-1, 0)) 28 | 29 | print(sum(buffer[(zero_idx + (i+1) * 1000) % len(buffer)][1] 30 | for i in range(3))) 31 | 32 | 33 | @profiler 34 | def part2(): 35 | input = [int(l) * 811589153 for l in open("input.txt")] 36 | 37 | buffer = [(idx, i) for idx, i in enumerate(input)] 38 | 39 | for _ in range(10): 40 | for idx, i in enumerate(input): 41 | old_idx = buffer.index((idx, i)) 42 | 43 | buffer.remove((idx, i)) 44 | buffer.insert((old_idx + i + len(input) - 1) % 45 | (len(input) - 1), (idx, i)) 46 | 47 | zero_idx = buffer.index((input.index(0), 0)) 48 | print(sum(buffer[(zero_idx + (i+1) * 1000) % len(buffer)][1] 49 | for i in range(3))) 50 | 51 | 52 | if __name__ == "__main__": 53 | 54 | part1() 55 | part2() 56 | -------------------------------------------------------------------------------- /2022/day20/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | use std::fs; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | fs::read_to_string("input.txt").unwrap().split("\n"); 14 | } 15 | 16 | fn part_2() { 17 | fs::read_to_string("input.txt").unwrap().split("\n"); 18 | } 19 | 20 | fn main() { 21 | bench(part_1); 22 | bench(part_2); 23 | } 24 | -------------------------------------------------------------------------------- /2022/day22/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | use std::fs; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | fs::read_to_string("input.txt").unwrap().split("\n"); 14 | } 15 | 16 | fn part_2() { 17 | fs::read_to_string("input.txt").unwrap().split("\n"); 18 | } 19 | 20 | fn main() { 21 | bench(part_1); 22 | bench(part_2); 23 | } 24 | -------------------------------------------------------------------------------- /2022/day25/code.py: -------------------------------------------------------------------------------- 1 | from time import time as perf_counter 2 | 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = perf_counter() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(perf_counter()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | 14 | def get_decimal(snafu): 15 | ret = 0 16 | for idx, c in enumerate(snafu[::-1]): 17 | if c.isnumeric(): 18 | ret += int(c) * 5**idx 19 | elif c == "-": 20 | ret += -1 * 5**idx 21 | elif c == "=": 22 | ret += -2 * 5**idx 23 | 24 | return ret 25 | 26 | 27 | def get_snafu(n): 28 | 29 | ret = "" 30 | 31 | while n != 0: 32 | n, current_digit = divmod(n, 5) 33 | if current_digit in [0, 1, 2]: 34 | ret += str(current_digit) 35 | elif current_digit == 3: 36 | ret += "=" 37 | n += 1 38 | elif current_digit == 4: 39 | ret += "-" 40 | n += 1 41 | 42 | return ret[::-1] 43 | 44 | 45 | @profiler 46 | def part1(): 47 | print(get_snafu(sum(map(get_decimal, open("input.txt").read().splitlines())))) 48 | 49 | if __name__ == "__main__": 50 | 51 | part1() 52 | -------------------------------------------------------------------------------- /2022/day25/main.rs: -------------------------------------------------------------------------------- 1 | use std::fs; 2 | use std::time; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn get_decimal(snafu: &str) -> i64 { 13 | let mut ret: i64 = 0; 14 | 15 | for (idx, c) in snafu.chars().rev().enumerate() { 16 | match c { 17 | c if c.is_numeric() => { 18 | ret += c.to_digit(10).unwrap() as i64 * 5i64.pow(idx.try_into().unwrap()); 19 | } 20 | '-' => { 21 | ret -= 5i64.pow(idx.try_into().unwrap()); 22 | } 23 | '=' => { 24 | ret -= 2 * 5i64.pow(idx.try_into().unwrap()); 25 | } 26 | _ => panic!(), 27 | } 28 | } 29 | 30 | ret 31 | } 32 | fn get_snafu(mut n: i64) -> String { 33 | let mut ret: String = String::new(); 34 | while n > 0 { 35 | let current_digit = n % 5; 36 | n /= 5; 37 | match current_digit { 38 | 0..=2 => ret.push(char::from_digit(current_digit as u32, 10).unwrap()), 39 | 3 => { 40 | ret.push('='); 41 | n += 1; 42 | } 43 | 4 => { 44 | ret.push('-'); 45 | n += 1; 46 | } 47 | _ => unreachable!(), 48 | } 49 | } 50 | ret.chars().rev().collect() 51 | } 52 | fn part_1() { 53 | println!( 54 | "{}", 55 | get_snafu( 56 | fs::read_to_string("input.txt") 57 | .unwrap() 58 | .lines() 59 | .map(|x| get_decimal(x)) 60 | .sum::(), 61 | ) 62 | ); 63 | } 64 | 65 | fn main() { 66 | bench(part_1); 67 | } 68 | -------------------------------------------------------------------------------- /2022/template/code.py: -------------------------------------------------------------------------------- 1 | from time import perf_counter 2 | 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = perf_counter() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(perf_counter()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | pass 17 | 18 | 19 | @profiler 20 | def part2(): 21 | pass 22 | 23 | 24 | if __name__ == "__main__": 25 | 26 | part1() 27 | part2() 28 | -------------------------------------------------------------------------------- /2022/template/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | use std::fs; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | fs::read_to_string("input.txt").unwrap().split("\n"); 14 | } 15 | 16 | fn part_2() { 17 | fs::read_to_string("input.txt").unwrap().split("\n"); 18 | } 19 | 20 | fn main() { 21 | bench(part_1); 22 | bench(part_2); 23 | } 24 | -------------------------------------------------------------------------------- /2023/Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "advent_of_code" 3 | version = "0.1.0" 4 | edition = "2021" 5 | 6 | [dependencies] 7 | regex="1.4.2" 8 | 9 | [[bin]] 10 | name="template" 11 | path="template/main.rs" 12 | 13 | [[bin]] 14 | name="day01" 15 | path="day01/main.rs" 16 | 17 | [[bin]] 18 | name="day02" 19 | path="day02/main.rs" 20 | 21 | [[bin]] 22 | name="day03" 23 | path="day03/main.rs" 24 | 25 | [[bin]] 26 | name="day04" 27 | path="day04/main.rs" 28 | 29 | 30 | [[bin]] 31 | name="day06" 32 | path="day06/main.rs" 33 | 34 | 35 | 36 | [[bin]] 37 | name="day09" 38 | path="day09/main.rs" 39 | 40 | [[bin]] 41 | name="day18" 42 | path="day18/main.rs" -------------------------------------------------------------------------------- /2023/day01/code.py: -------------------------------------------------------------------------------- 1 | from time import perf_counter 2 | import re 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = perf_counter() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(perf_counter()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | total = 0 17 | 18 | for l in open("day01/input.txt"): 19 | d = re.findall(r"\d" , l) 20 | 21 | total += int(d[0] + d[-1]) 22 | 23 | print(total) 24 | 25 | @profiler 26 | def part2(): 27 | 28 | vals = { 29 | "one" : "1", 30 | "two" : "2", 31 | "three" : "3", 32 | "four" : "4", 33 | "five" : "5", 34 | "six" : "6", 35 | "seven" : "7", 36 | "eight" : "8", 37 | "nine" : "9", 38 | "zero" : "0", 39 | 40 | } 41 | total = 0 42 | 43 | for l in open("day01/input.txt"): 44 | words = re.findall("(?=(" + "|".join(vals.keys()) + "|\d))" , l) 45 | 46 | total += int("".join([ d if d.isdigit() else vals[d] for d in [words[0] , words[-1]]])) 47 | 48 | print(total) 49 | 50 | if __name__ == "__main__": 51 | 52 | part1() 53 | part2() 54 | -------------------------------------------------------------------------------- /2023/day01/main.rs: -------------------------------------------------------------------------------- 1 | use std::collections::HashMap; 2 | use std::fs; 3 | use std::time; 4 | 5 | fn bench(f: fn()) { 6 | let t0 = time::Instant::now(); 7 | let ret = f(); 8 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 9 | 10 | ret 11 | } 12 | 13 | fn part_1() { 14 | let mut total = 0u32; 15 | for l in fs::read_to_string("day01/input.txt").unwrap().split("\n") { 16 | let digits: Vec<_> = l.chars().filter_map(|a| a.to_digit(10)).collect(); 17 | 18 | total += digits.get(0).unwrap() * 10u32 + digits.get(digits.len() - 1).unwrap(); 19 | } 20 | dbg!(total); 21 | } 22 | 23 | fn part_2() { 24 | let mut total = 0u32; 25 | 26 | let vals: HashMap<&str, char> = [ 27 | ("one", '1'), 28 | ("two", '2'), 29 | ("three", '3'), 30 | ("four", '4'), 31 | ("five", '5'), 32 | ("six", '6'), 33 | ("seven", '7'), 34 | ("eight", '8'), 35 | ("nine", '9'), 36 | ("zero", '0'), 37 | ] 38 | .iter() 39 | .cloned() 40 | .collect(); 41 | 42 | for l in fs::read_to_string("day01/input.txt").unwrap().split("\n") { 43 | let mut line = l.to_owned(); 44 | let mut digits = Vec::::new(); 45 | while line.len() > 0 { 46 | if line.chars().nth(0).unwrap().is_digit(10) { 47 | digits.push(line.chars().nth(0).unwrap()); 48 | } else { 49 | for d in vals.keys() { 50 | if line.starts_with(d) { 51 | digits.push(vals.get(d).unwrap().clone()); 52 | break; 53 | } 54 | } 55 | } 56 | line.remove(0); 57 | } 58 | total += digits.get(0).unwrap().to_digit(10).unwrap() * 10u32 59 | + digits.get(digits.len() - 1).unwrap().to_digit(10).unwrap(); 60 | } 61 | dbg!(total); 62 | } 63 | 64 | fn main() { 65 | bench(part_1); 66 | bench(part_2); 67 | } 68 | -------------------------------------------------------------------------------- /2023/day02/code.py: -------------------------------------------------------------------------------- 1 | from time import perf_counter 2 | import re 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = perf_counter() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(perf_counter()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | 14 | @profiler 15 | def part1(): 16 | total = 0 17 | 18 | for l in open("day02/input.txt"): 19 | 20 | red_cnt = max(map(int,re.findall(r"(\d+) red",l))) 21 | green_cnt = max(map(int,re.findall(r"(\d+) green",l))) 22 | blue_cnt = max(map(int,re.findall(r"(\d+) blue",l))) 23 | 24 | id = int(re.findall(r"Game (\d+)",l)[0]) 25 | 26 | if red_cnt <= 12 and green_cnt <=13 and blue_cnt<=14: 27 | total += id 28 | 29 | print(total) 30 | 31 | 32 | @profiler 33 | def part2(): 34 | total = 0 35 | 36 | for l in open("day02/input.txt"): 37 | 38 | red_cnt = max(map(int,re.findall(r"(\d+) red",l))) 39 | green_cnt = max(map(int,re.findall(r"(\d+) green",l))) 40 | blue_cnt = max(map(int,re.findall(r"(\d+) blue",l))) 41 | 42 | total += red_cnt * green_cnt * blue_cnt 43 | 44 | print(total) 45 | 46 | 47 | if __name__ == "__main__": 48 | 49 | part1() 50 | part2() 51 | -------------------------------------------------------------------------------- /2023/day03/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | use std::fs; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 14 | } 15 | 16 | fn part_2() { 17 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 18 | } 19 | 20 | fn main() { 21 | bench(part_1); 22 | bench(part_2); 23 | } 24 | -------------------------------------------------------------------------------- /2023/day04/code.py: -------------------------------------------------------------------------------- 1 | from time import perf_counter 2 | from collections import defaultdict 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = perf_counter() 8 | ret = method(*arg, **kw) 9 | print('Method ' + method.__name__ + ' took : ' + 10 | "{:2.5f}".format(perf_counter()-t) + ' sec') 11 | return ret 12 | return wrapper_method 13 | 14 | 15 | 16 | @profiler 17 | def part1(): 18 | total = 0 19 | 20 | for l in open("day04/input.txt"): 21 | ticket = l.split(":")[1].split("|") 22 | 23 | winning = set(map(int,ticket[0].split())) 24 | nums = set(map(int,ticket[1].split())) 25 | 26 | total += int(2 ** (len(winning.intersection(nums)) - 1)) 27 | 28 | print(total) 29 | 30 | 31 | @profiler 32 | def part2(): 33 | 34 | ticket_count = defaultdict(int) 35 | 36 | for card,l in enumerate(open("day04/input.txt")): 37 | ticket = l.split(":")[1].split("|") 38 | 39 | ticket_count[card+1] += 1 40 | 41 | winning = set(map(int,ticket[0].split())) 42 | nums = set(map(int,ticket[1].split())) 43 | 44 | for n in range(len(winning.intersection(nums))): 45 | ticket_count[card + 2 + n] += ticket_count[card+1] 46 | 47 | print(sum(ticket_count.values())) 48 | 49 | 50 | if __name__ == "__main__": 51 | 52 | part1() 53 | part2() 54 | -------------------------------------------------------------------------------- /2023/day04/main.rs: -------------------------------------------------------------------------------- 1 | use std::collections::{HashMap, HashSet}; 2 | use std::time; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | let mut total = 0u16; 14 | 15 | for l in include_str!("input.txt").split("\n") { 16 | let ticket = l 17 | .split(":") 18 | .nth(1) 19 | .unwrap() 20 | .split("|") 21 | .map(|s| s.split_whitespace().collect::>()) 22 | .collect::>(); 23 | 24 | let cnt =ticket 25 | .get(0) 26 | .unwrap() 27 | .intersection(ticket.get(1).unwrap()) 28 | .count(); 29 | if cnt > 0{ 30 | total += 2u16.pow(cnt as u32 -1 ); 31 | } 32 | 33 | } 34 | 35 | dbg!(total); 36 | } 37 | 38 | fn part_2() { 39 | let mut ticket_count: HashMap = HashMap::new(); 40 | 41 | for (card, l) in include_str!("input.txt").split("\n").enumerate() { 42 | *ticket_count.entry(card as u16 + 1).or_insert(0) += 1; 43 | 44 | let ticket = l 45 | .split(":") 46 | .nth(1) 47 | .unwrap() 48 | .split("|") 49 | .map(|s| s.split_whitespace().collect::>()) 50 | .collect::>(); 51 | 52 | let cnt = ticket 53 | .get(0) 54 | .unwrap() 55 | .intersection(ticket.get(1).unwrap()) 56 | .count(); 57 | 58 | for n in 0..cnt { 59 | let num = ticket_count.get(&(card as u16 + 1)).unwrap().clone(); 60 | *ticket_count.entry(card as u16 + 2 + n as u16).or_insert(0) += num; 61 | } 62 | } 63 | dbg!(ticket_count.values().sum::()); 64 | } 65 | 66 | fn main() { 67 | bench(part_1); 68 | bench(part_2); 69 | } 70 | -------------------------------------------------------------------------------- /2023/day05/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | use std::fs; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 14 | } 15 | 16 | fn part_2() { 17 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 18 | } 19 | 20 | fn main() { 21 | bench(part_1); 22 | bench(part_2); 23 | } 24 | -------------------------------------------------------------------------------- /2023/day06/code.py: -------------------------------------------------------------------------------- 1 | from time import perf_counter 2 | from math import ceil,floor 3 | 4 | def profiler(method): 5 | def wrapper_method(*arg, **kw): 6 | t = perf_counter() 7 | ret = method(*arg, **kw) 8 | print('Method ' + method.__name__ + ' took : ' + 9 | "{:2.5f}".format(perf_counter()-t) + ' sec') 10 | return ret 11 | return wrapper_method 12 | 13 | @profiler 14 | def part1(): 15 | input = [] 16 | for l in open("day06/input.txt"): 17 | input.append(list(map(int,l.split()[1:]))) 18 | 19 | total = 1 20 | for tt,d in zip(input[0],input[1]): 21 | wins = 0 22 | for t in range(tt+1): 23 | if (tt-t)*t > d: 24 | wins += 1 25 | total *= wins 26 | print(total) 27 | 28 | 29 | @profiler 30 | def part2(): 31 | input = [] 32 | for l in open("day06/input.txt"): 33 | input.append(int("".join(l.split()[1:]))) 34 | 35 | tt = input[0] 36 | d = input[1] 37 | 38 | wins_t = ceil((tt - (tt*tt - 4 *d )**0.5)/2) 39 | loss_t = floor((tt + (tt*tt - 4 *d )**0.5)/2) 40 | 41 | print(loss_t - wins_t) 42 | 43 | if __name__ == "__main__": 44 | 45 | part1() 46 | part2() 47 | -------------------------------------------------------------------------------- /2023/day06/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | 3 | fn bench(f: fn()) { 4 | let t0 = time::Instant::now(); 5 | let ret = f(); 6 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 7 | 8 | ret 9 | } 10 | 11 | fn part_1() { 12 | let mut input: Vec> = Vec::new(); 13 | 14 | for l in include_str!("input.txt").split("\n") { 15 | let t = l 16 | .split_whitespace() 17 | .into_iter() 18 | .skip(1) 19 | .map(|num| num.parse::().unwrap()) 20 | .collect::>(); 21 | input.push(t); 22 | } 23 | let mut total = 1u32; 24 | for i in 0..input.get(0).unwrap().len() { 25 | let tt = input.get(0).unwrap().get(i).unwrap(); 26 | let d: &u16 = input.get(1).unwrap().get(i).unwrap(); 27 | 28 | let mut wins = 0u16; 29 | for t in 0..=*tt { 30 | if (tt - t) * t > *d { 31 | wins += 1; 32 | } 33 | } 34 | total *= wins as u32; 35 | } 36 | dbg!(total); 37 | } 38 | 39 | fn part_2() { 40 | let mut input: Vec = Vec::new(); 41 | for l in include_str!("input.txt").split("\n") { 42 | let t = l 43 | .split_whitespace() 44 | .into_iter() 45 | .skip(1) 46 | .collect::>() 47 | .join(""); 48 | input.push(t.parse::().unwrap()); 49 | } 50 | 51 | let mut wins_t = 0u64; 52 | let mut loss_t = 0u64; 53 | 54 | let tt = input.get(0).unwrap().clone(); 55 | let d: u64 = input.get(1).unwrap().clone(); 56 | 57 | let wins = ((tt as f32 - ((tt*tt - 4 *d ) as f32).sqrt()) / 2.0).ceil() as u32; 58 | let loss = ((tt as f32 + ((tt*tt - 4 *d ) as f32).sqrt()) / 2.0).floor() as u32; 59 | 60 | dbg!(loss - wins); 61 | } 62 | 63 | fn main() { 64 | bench(part_1); 65 | bench(part_2); 66 | } 67 | -------------------------------------------------------------------------------- /2023/day07/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | use std::fs; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 14 | } 15 | 16 | fn part_2() { 17 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 18 | } 19 | 20 | fn main() { 21 | bench(part_1); 22 | bench(part_2); 23 | } 24 | -------------------------------------------------------------------------------- /2023/day08/code.py: -------------------------------------------------------------------------------- 1 | from time import perf_counter 2 | import re 3 | from math import prod 4 | 5 | 6 | def profiler(method): 7 | def wrapper_method(*arg, **kw): 8 | t = perf_counter() 9 | ret = method(*arg, **kw) 10 | print("Method " + method.__name__ + " took : " + "{:2.5f}".format(perf_counter() - t) + " sec") 11 | return ret 12 | 13 | return wrapper_method 14 | 15 | 16 | @profiler 17 | def part1(): 18 | input = open("day08/input.txt").read().split("\n\n") 19 | 20 | directions = input[0] 21 | 22 | maze = {} 23 | for l in input[1].splitlines(): 24 | p = re.findall(r"\w{3}", l) 25 | maze[p[0]] = (p[1], p[2]) 26 | 27 | state = "AAA" 28 | 29 | idx = 0 30 | while state != "ZZZ": 31 | match directions[idx % len(directions)]: 32 | case "R": 33 | state = maze[state][1] 34 | case "L": 35 | state = maze[state][0] 36 | 37 | idx += 1 38 | print(idx) 39 | 40 | 41 | def get_distance(maze, directions, start): 42 | state = start 43 | idx = 0 44 | 45 | while state[2] != "Z": 46 | match directions[idx % len(directions)]: 47 | case "R": 48 | state = maze[state][1] 49 | case "L": 50 | state = maze[state][0] 51 | 52 | idx += 1 53 | 54 | return idx 55 | 56 | 57 | @profiler 58 | def part2(): 59 | input = open("day08/input.txt").read().split("\n\n") 60 | 61 | directions = input[0] 62 | 63 | maze = {} 64 | 65 | As = [] 66 | 67 | for l in input[1].splitlines(): 68 | p = re.findall(r"\w{3}", l) 69 | maze[p[0]] = (p[1], p[2]) 70 | if p[0][2] == "A": 71 | As.append(p[0]) 72 | 73 | dist = [get_distance(maze, directions, a) // len(directions) for a in As] 74 | 75 | print(prod(dist) * len(directions)) 76 | 77 | 78 | if __name__ == "__main__": 79 | part1() 80 | part2() 81 | -------------------------------------------------------------------------------- /2023/day08/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | use std::fs; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 14 | } 15 | 16 | fn part_2() { 17 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 18 | } 19 | 20 | fn main() { 21 | bench(part_1); 22 | bench(part_2); 23 | } 24 | -------------------------------------------------------------------------------- /2023/day09/code.py: -------------------------------------------------------------------------------- 1 | # pylint: disable=C0114,C0116,C0301,C0209,W1514 2 | 3 | from time import perf_counter 4 | 5 | 6 | def profiler(method): 7 | def wrapper_method(*arg, **kw): 8 | t = perf_counter() 9 | ret = method(*arg, **kw) 10 | print("Method " + method.__name__ + " took : " + "{:2.5f}".format(perf_counter() - t) + " sec") 11 | return ret 12 | 13 | return wrapper_method 14 | 15 | 16 | def get_next(l): 17 | m = [] 18 | m.append(l) 19 | while len(set(m[-1])) > 1: 20 | new_l = [] 21 | for i in range(1, len(m[-1])): 22 | new_l.append(m[-1][i] - m[-1][i - 1]) 23 | m.append(new_l) 24 | 25 | for i in reversed(range(len(m) - 1)): 26 | m[i].append(m[i + 1][-1] + m[i][-1]) 27 | return m[0][-1] 28 | 29 | 30 | @profiler 31 | def part1(): 32 | oasis = [list(map(int, l.split())) for l in open("day09/input.txt").read().splitlines()] 33 | 34 | print(sum([get_next(v) for v in oasis])) 35 | 36 | 37 | @profiler 38 | def part2(): 39 | oasis = [list(map(int, l.split())) for l in open("day09/input.txt").read().splitlines()] 40 | 41 | print(sum([get_next(v[::-1]) for v in oasis])) 42 | 43 | 44 | if __name__ == "__main__": 45 | part1() 46 | part2() 47 | -------------------------------------------------------------------------------- /2023/day09/main.rs: -------------------------------------------------------------------------------- 1 | use std::collections::HashSet; 2 | use std::time; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | fn get_next(l: Vec) -> i32 { 12 | let mut m: Vec> = Vec::new(); 13 | m.push(l.clone()); 14 | 15 | while HashSet::::from_iter(m.last().cloned().unwrap()).len() > 1 { 16 | let mut new_l: Vec = Vec::new(); 17 | for i in 1..(m.last().unwrap().len()) { 18 | new_l.push(m.last().unwrap().get(i).unwrap() - m.last().unwrap().get(i - 1).unwrap()); 19 | } 20 | m.push(new_l); 21 | } 22 | 23 | for i in (0..(&m.len() - 1)).rev() { 24 | let d = m.get(i + 1).unwrap().last().unwrap().clone(); 25 | let last = m.get(i).unwrap().last().unwrap().clone(); 26 | m.get_mut(i).unwrap().push(last + d); 27 | } 28 | 29 | m.first().unwrap().last().unwrap().clone() 30 | } 31 | 32 | fn part_1() { 33 | let next: i32 = include_str!("input.txt") 34 | .split("\n") 35 | .map(|l| { 36 | l.split(' ') 37 | .map(|c| c.parse::().unwrap()) 38 | .collect::>() 39 | }) 40 | .map(get_next) 41 | .sum(); 42 | 43 | dbg!(next); 44 | } 45 | 46 | fn part_2() { 47 | let prev: i32 = include_str!("input.txt") 48 | .split("\n") 49 | .map(|l| { 50 | l.split(' ') 51 | .map(|c| c.parse::().unwrap()) 52 | .rev() 53 | .collect::>() 54 | }) 55 | .map(get_next) 56 | .sum(); 57 | 58 | dbg!(prev); 59 | } 60 | 61 | fn main() { 62 | bench(part_1); 63 | bench(part_2); 64 | } 65 | -------------------------------------------------------------------------------- /2023/day12/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | use std::fs; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 14 | } 15 | 16 | fn part_2() { 17 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 18 | } 19 | 20 | fn main() { 21 | bench(part_1); 22 | bench(part_2); 23 | } 24 | -------------------------------------------------------------------------------- /2023/day15/code.py: -------------------------------------------------------------------------------- 1 | # pylint: disable=C0114,C0116,C0301,C0209,W1514 2 | 3 | from time import perf_counter 4 | from functools import cache 5 | import re 6 | 7 | 8 | def profiler(method): 9 | def wrapper_method(*arg, **kw): 10 | t = perf_counter() 11 | ret = method(*arg, **kw) 12 | print("Method " + method.__name__ + " took : " + "{:2.5f}".format(perf_counter() - t) + " sec") 13 | return ret 14 | 15 | return wrapper_method 16 | 17 | 18 | @cache 19 | def get_hash(st): 20 | hash_res = 0 21 | for c in st: 22 | hash_res += ord(c) 23 | hash_res *= 17 24 | hash_res %= 256 25 | 26 | return hash_res 27 | 28 | 29 | @profiler 30 | def part1(): 31 | print(sum(map(get_hash, open("day15/input.txt").read().split(",")))) 32 | 33 | 34 | @profiler 35 | def part2(): 36 | seq = open("day15/input.txt").read().split(",") 37 | 38 | boxes = [{} for _ in range(256)] 39 | 40 | for s in seq: 41 | label = re.findall(r"\w+", s)[0] 42 | box = get_hash(label) 43 | op = s.replace(label, "") 44 | 45 | match op[0]: 46 | case "-": 47 | if label in boxes[box]: 48 | del boxes[box][label] 49 | case "=": 50 | boxes[box][label] = int(op[-1]) 51 | 52 | print(sum((i + 1) * (l + 1) * (boxes[i][b]) for i in range(256) for l, b in enumerate((boxes[i])))) 53 | 54 | 55 | if __name__ == "__main__": 56 | part1() 57 | part2() 58 | -------------------------------------------------------------------------------- /2023/day18/code.py: -------------------------------------------------------------------------------- 1 | # pylint: disable=C0114,C0116,C0301,C0209,W1514 2 | 3 | from time import perf_counter 4 | 5 | 6 | def profiler(method): 7 | def wrapper_method(*arg, **kw): 8 | t = perf_counter() 9 | ret = method(*arg, **kw) 10 | print("Method " + method.__name__ + " took : " + "{:2.5f}".format(perf_counter() - t) + " sec") 11 | return ret 12 | 13 | return wrapper_method 14 | 15 | 16 | def shoe_lace(points): 17 | res = sum(points[i - 1][0] * points[i][1] - points[i - 1][1] * points[i][0] for i in range(len(points))) 18 | return res // 2 19 | 20 | 21 | @profiler 22 | def part1(): 23 | polygon = [(0, 0)] 24 | 25 | deltas = {"R": (1, 0), "L": (-1, 0), "U": (0, -1), "D": (0, 1)} 26 | 27 | p_cnt = 0 28 | 29 | for l in open("day18/input.txt"): 30 | ps = l.split() 31 | d = deltas[ps[0]] 32 | lp = polygon[-1] 33 | steps = int(ps[1]) 34 | p_cnt += steps 35 | polygon.append((lp[0] + d[0] * steps, lp[1] + d[1] * steps)) 36 | 37 | print(shoe_lace(polygon) + p_cnt // 2 + 1) 38 | 39 | 40 | @profiler 41 | def part2(): 42 | polygon = [(0, 0)] 43 | 44 | deltas = {"0": (1, 0), "2": (-1, 0), "3": (0, -1), "1": (0, 1)} 45 | 46 | p_cnt = 0 47 | 48 | for l in open("day18/input.txt"): 49 | ps = l.split() 50 | 51 | d = deltas[ps[2][-2]] 52 | lp = polygon[-1] 53 | steps = int(ps[2][2:-2], 16) 54 | 55 | p_cnt += steps 56 | polygon.append((lp[0] + d[0] * steps, lp[1] + d[1] * steps)) 57 | 58 | print(shoe_lace(polygon) + (p_cnt + 1) // 2 + 1) 59 | 60 | 61 | if __name__ == "__main__": 62 | part1() 63 | part2() 64 | -------------------------------------------------------------------------------- /2023/day23/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | use std::fs; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 14 | } 15 | 16 | fn part_2() { 17 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 18 | } 19 | 20 | fn main() { 21 | bench(part_1); 22 | bench(part_2); 23 | } 24 | -------------------------------------------------------------------------------- /2023/day25/code.py: -------------------------------------------------------------------------------- 1 | from time import perf_counter 2 | import networkx 3 | 4 | 5 | def profiler(method): 6 | def wrapper_method(*arg, **kw): 7 | t = perf_counter() 8 | ret = method(*arg, **kw) 9 | print("Method " + method.__name__ + " took : " + "{:2.5f}".format(perf_counter() - t) + " sec") 10 | return ret 11 | 12 | return wrapper_method 13 | 14 | 15 | @profiler 16 | def part1(): 17 | graph = networkx.Graph() 18 | 19 | for l in open("day25/input.txt"): 20 | src, dst = l.strip().split(": ") 21 | 22 | for n in dst.split(): 23 | graph.add_edge(src, n) 24 | 25 | _, partitions = networkx.stoer_wagner(graph) 26 | 27 | print(len(partitions[0]) * len(partitions[1])) 28 | 29 | 30 | if __name__ == "__main__": 31 | part1() 32 | -------------------------------------------------------------------------------- /2023/day25/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | use std::fs; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 14 | } 15 | 16 | fn part_2() { 17 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 18 | } 19 | 20 | fn main() { 21 | bench(part_1); 22 | bench(part_2); 23 | } 24 | -------------------------------------------------------------------------------- /2023/template/code.py: -------------------------------------------------------------------------------- 1 | # pylint: disable=C0114,C0116,C0301,C0209,W1514 2 | 3 | from time import perf_counter 4 | 5 | 6 | def profiler(method): 7 | def wrapper_method(*arg, **kw): 8 | t = perf_counter() 9 | ret = method(*arg, **kw) 10 | print("Method " + method.__name__ + " took : " + "{:2.5f}".format(perf_counter() - t) + " sec") 11 | return ret 12 | 13 | return wrapper_method 14 | 15 | 16 | @profiler 17 | def part1(): 18 | pass 19 | 20 | 21 | @profiler 22 | def part2(): 23 | pass 24 | 25 | 26 | if __name__ == "__main__": 27 | part1() 28 | part2() 29 | -------------------------------------------------------------------------------- /2023/template/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | use std::fs; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 14 | } 15 | 16 | fn part_2() { 17 | fs::read_to_string("template/input.txt").unwrap().split("\n"); 18 | } 19 | 20 | fn main() { 21 | bench(part_1); 22 | bench(part_2); 23 | } 24 | -------------------------------------------------------------------------------- /2024/Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "advent_of_code" 3 | version = "0.1.0" 4 | edition = "2021" 5 | 6 | [dependencies] 7 | regex="1.4.2" 8 | itertools = "0.13.0" 9 | 10 | 11 | [[bin]] 12 | name="template" 13 | path="template/main.rs" 14 | 15 | [[bin]] 16 | name="day01" 17 | path="day01/main.rs" 18 | 19 | [[bin]] 20 | name="day02" 21 | path="day02/main.rs" 22 | 23 | [[bin]] 24 | name="day03" 25 | path="day03/main.rs" 26 | 27 | [[bin]] 28 | name="day04" 29 | path="day04/main.rs" 30 | 31 | [[bin]] 32 | name="day05" 33 | path="day05/main.rs" 34 | 35 | [[bin]] 36 | name="day06" 37 | path="day06/main.rs" 38 | 39 | [[bin]] 40 | name="day07" 41 | path="day07/main.rs" 42 | 43 | [[bin]] 44 | name="day08" 45 | path="day08/main.rs" 46 | 47 | [[bin]] 48 | name="day09" 49 | path="day09/main.rs" 50 | 51 | [[bin]] 52 | name="day10" 53 | path="day10/main.rs" 54 | 55 | [[bin]] 56 | name="day11" 57 | path="day11/main.rs" 58 | 59 | [[bin]] 60 | name="day12" 61 | path="day12/main.rs" 62 | 63 | [[bin]] 64 | name="day13" 65 | path="day13/main.rs" 66 | 67 | [[bin]] 68 | name="day14" 69 | path="day14/main.rs" 70 | 71 | [[bin]] 72 | name="day15" 73 | path="day15/main.rs" 74 | 75 | [[bin]] 76 | name="day16" 77 | path="day16/main.rs" 78 | 79 | [[bin]] 80 | name="day17" 81 | path="day17/main.rs" 82 | 83 | 84 | [[bin]] 85 | name="day18" 86 | path="day18/main.rs" 87 | 88 | [[bin]] 89 | name="day19" 90 | path="day19/main.rs" 91 | 92 | [[bin]] 93 | name="day20" 94 | path="day20/main.rs" 95 | 96 | [[bin]] 97 | name="day21" 98 | path="day21/main.rs" 99 | 100 | [[bin]] 101 | name="day22" 102 | path="day22/main.rs" 103 | 104 | [[bin]] 105 | name="day23" 106 | path="day23/main.rs" 107 | 108 | [[bin]] 109 | name="day24" 110 | path="day24/main.rs" 111 | 112 | [[bin]] 113 | name="day25" 114 | path="day25/main.rs" 115 | -------------------------------------------------------------------------------- /2024/create_template.py: -------------------------------------------------------------------------------- 1 | import shutil 2 | import os 3 | import sys 4 | import subprocess 5 | 6 | 7 | def create_day_folder(day_number): 8 | 9 | if not (0 <= day_number <= 25): 10 | raise ValueError("Day number must be between 00 and 25") 11 | 12 | day_str = str(day_number).zfill(2) # Add leading zero if needed 13 | day_folder = f"day{day_str}" 14 | 15 | # Copy the template folder 16 | shutil.copytree("template", day_folder) 17 | 18 | # Update Cargo.toml 19 | with open("Cargo.toml", "r") as f: 20 | lines = f.readlines() 21 | 22 | found_day = False 23 | with open("Cargo.toml", "w") as f: 24 | for line in lines: 25 | if line.startswith(f"name=\"day{day_str}\""): 26 | found_day = True 27 | f.write(line) 28 | if not found_day: 29 | f.write(f"\n[[bin]]\nname=\"day{ 30 | day_str}\"\npath=\"day{day_str}/main.rs\"\n") 31 | 32 | subprocess.run(["git", "add", day_folder]) 33 | subprocess.run(["git", "add", "Cargo.toml"]) 34 | subprocess.run(["git", "commit", "-m", f"Adding day {day_str} template"]) 35 | subprocess.run(["git", "push"]) 36 | 37 | 38 | if __name__ == "__main__": 39 | if len(sys.argv) != 2: 40 | print("Usage: python script.py ") 41 | sys.exit(1) 42 | 43 | try: 44 | day_number = int(sys.argv[1]) 45 | create_day_folder(day_number) 46 | # Git commands 47 | 48 | except ValueError: 49 | print("Invalid day number. Please provide an integer between 00 and 25.") 50 | sys.exit(1) 51 | -------------------------------------------------------------------------------- /2024/day01/code.py: -------------------------------------------------------------------------------- 1 | # pylint: disable=C0114,C0116,C0301,C0209,W1514 2 | 3 | from time import perf_counter 4 | from collections import Counter 5 | 6 | 7 | def profiler(method): 8 | def wrapper_method(*arg, **kw): 9 | t = perf_counter() 10 | ret = method(*arg, **kw) 11 | print( 12 | "Method " 13 | + method.__name__ 14 | + " took : " 15 | + "{:2.5f}".format(perf_counter() - t) 16 | + " sec" 17 | ) 18 | return ret 19 | 20 | return wrapper_method 21 | 22 | 23 | @profiler 24 | def part1(): 25 | l1, l2 = list(), list() 26 | for l in open("day01/input.txt"): 27 | p = l.strip().split() 28 | l1.append(int(p[0])) 29 | l2.append(int(p[1])) 30 | 31 | l1.sort() 32 | l2.sort() 33 | 34 | print(sum(abs(a - b) for a, b in zip(l1, l2))) 35 | 36 | @profiler 37 | def part2(): 38 | l1, l2 = list(), list() 39 | for l in open("day01/input.txt"): 40 | p = l.strip().split() 41 | l1.append(int(p[0])) 42 | l2.append(int(p[1])) 43 | 44 | c = Counter(l2) 45 | 46 | print(sum(l * c[l] for l in l1)) 47 | 48 | 49 | if __name__ == "__main__": 50 | part1() 51 | part2() 52 | -------------------------------------------------------------------------------- /2024/day01/main.rs: -------------------------------------------------------------------------------- 1 | use std::collections::HashMap; 2 | use std::time; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | 12 | fn part_1() { 13 | let mut l1: Vec = Vec::new(); 14 | let mut l2: Vec = Vec::new(); 15 | 16 | for line in include_str!("input.txt").split("\n") { 17 | let parts: Vec<&str> = line.split_whitespace().collect(); 18 | if parts.len() == 2 { 19 | let a: i32 = parts[0].parse().unwrap(); 20 | let b: i32 = parts[1].parse().unwrap(); 21 | l1.push(a); 22 | l2.push(b); 23 | } 24 | } 25 | 26 | l1.sort(); 27 | l2.sort(); 28 | 29 | println!( 30 | "{}", 31 | l1.iter() 32 | .zip(l2.iter()) 33 | .map(|(a, b)| (a - b).abs()) 34 | .sum::() 35 | ); 36 | } 37 | 38 | fn part_2() { 39 | let mut l1: Vec = Vec::new(); 40 | let mut l2: Vec = Vec::new(); 41 | 42 | for line in include_str!("input.txt").split("\n") { 43 | let parts: Vec<&str> = line.split_whitespace().collect(); 44 | if parts.len() == 2 { 45 | let a: i32 = parts[0].parse().unwrap(); 46 | let b: i32 = parts[1].parse().unwrap(); 47 | l1.push(a); 48 | l2.push(b); 49 | } 50 | } 51 | 52 | let mut count_map: HashMap = HashMap::new(); 53 | for &value in &l2 { 54 | *count_map.entry(value).or_insert(0) += 1; 55 | } 56 | 57 | println!( 58 | "{}", 59 | l1.iter() 60 | .map(|&l| l * count_map.get(&l).unwrap_or(&0)) 61 | .sum::() 62 | ); 63 | } 64 | 65 | fn main() { 66 | bench(part_1); 67 | bench(part_2); 68 | } 69 | -------------------------------------------------------------------------------- /2024/day02/code.py: -------------------------------------------------------------------------------- 1 | # pylint: disable=C0114,C0116,C0301,C0209,W1514 2 | 3 | from time import perf_counter 4 | 5 | 6 | def profiler(method): 7 | def wrapper_method(*arg, **kw): 8 | t = perf_counter() 9 | ret = method(*arg, **kw) 10 | print( 11 | "Method " 12 | + method.__name__ 13 | + " took : " 14 | + "{:2.5f}".format(perf_counter() - t) 15 | + " sec" 16 | ) 17 | return ret 18 | 19 | return wrapper_method 20 | 21 | 22 | def is_safe(l): 23 | if l not in [sorted(l), sorted(l)[::-1]]: 24 | return False 25 | for i in range(1, len(l)): 26 | if abs(l[i] - l[i - 1]) not in [1, 2, 3]: 27 | return False 28 | return True 29 | 30 | 31 | @profiler 32 | def part1(): 33 | reports = [list(map(int, l.split())) for l in open("day02/input.txt").readlines()] 34 | print(sum(is_safe(l) for l in reports)) 35 | 36 | 37 | def is_safe_tolerate(l): 38 | if is_safe(l): 39 | return True 40 | return any(is_safe(l[:i] + l[i + 1 :]) for i in range(len(l))) 41 | 42 | 43 | @profiler 44 | def part2(): 45 | reports = [list(map(int, l.split())) for l in open("day02/input.txt").readlines()] 46 | print(sum(is_safe_tolerate(l) for l in reports)) 47 | 48 | 49 | if __name__ == "__main__": 50 | part1() 51 | part2() 52 | -------------------------------------------------------------------------------- /2024/day02/main.rs: -------------------------------------------------------------------------------- 1 | use std::time; 2 | 3 | fn bench(f: fn()) { 4 | let t0 = time::Instant::now(); 5 | let ret = f(); 6 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 7 | 8 | ret 9 | } 10 | 11 | fn is_safe(l: &Vec) -> bool { 12 | let mut sorted_asc = l.clone(); 13 | sorted_asc.sort(); 14 | 15 | let mut sorted_desc = sorted_asc.clone(); 16 | sorted_desc.reverse(); 17 | 18 | if l != &sorted_asc && l != &sorted_desc { 19 | return false; 20 | } 21 | 22 | for i in 1..l.len() { 23 | if (l[i] - l[i - 1]).abs() > 3 || (l[i] - l[i - 1]).abs() < 1 { 24 | return false; 25 | } 26 | } 27 | 28 | true 29 | } 30 | 31 | fn part_1() { 32 | let input = include_str!("input.txt"); 33 | 34 | let reports: Vec> = input 35 | .lines() 36 | .map(|line| { 37 | line.split_whitespace() 38 | .map(|num| num.parse::().expect("Invalid number")) 39 | .collect() 40 | }) 41 | .collect(); 42 | println!("{}", reports.iter().filter(|line| is_safe(line)).count()); 43 | } 44 | 45 | fn is_safe_tolerate(l: &Vec) -> bool { 46 | if is_safe(&l) { 47 | return true; 48 | } 49 | for i in 0..l.len() { 50 | let mut modified = l.clone(); 51 | modified.remove(i); 52 | if is_safe(&modified) { 53 | return true; 54 | } 55 | } 56 | false 57 | } 58 | fn part_2() { 59 | let input = include_str!("input.txt"); 60 | 61 | let reports: Vec> = input 62 | .lines() 63 | .map(|line| { 64 | line.split_whitespace() 65 | .map(|num| num.parse::().expect("Invalid number")) 66 | .collect() 67 | }) 68 | .collect(); 69 | println!("{}", reports.iter().filter(|line| is_safe_tolerate(line)).count()); 70 | } 71 | 72 | fn main() { 73 | bench(part_1); 74 | bench(part_2); 75 | } 76 | -------------------------------------------------------------------------------- /2024/day03/code.py: -------------------------------------------------------------------------------- 1 | # pylint: disable=C0114,C0116,C0301,C0209,W1514 2 | 3 | from time import perf_counter 4 | import re 5 | 6 | 7 | def profiler(method): 8 | def wrapper_method(*arg, **kw): 9 | t = perf_counter() 10 | ret = method(*arg, **kw) 11 | print( 12 | "Method " 13 | + method.__name__ 14 | + " took : " 15 | + "{:2.5f}".format(perf_counter() - t) 16 | + " sec" 17 | ) 18 | return ret 19 | 20 | return wrapper_method 21 | 22 | def get_sum(input): 23 | pairs = re.findall(r"mul\((\d+),(\d+)\)", input) 24 | return sum(int(p[0]) * int(p[1]) for p in pairs) 25 | 26 | @profiler 27 | def part1(): 28 | print(get_sum(open("day03/input.txt").read())) 29 | 30 | @profiler 31 | def part2(): 32 | input = open("day03/input.txt").read() 33 | 34 | new_input = re.sub(r"don't\(\)[\s\S]*?do\(\)", "", input) 35 | 36 | print(get_sum(new_input)) 37 | 38 | 39 | if __name__ == "__main__": 40 | part1() 41 | part2() 42 | -------------------------------------------------------------------------------- /2024/day03/main.rs: -------------------------------------------------------------------------------- 1 | use regex::Regex; 2 | use std::time; 3 | 4 | fn bench(f: fn()) { 5 | let t0 = time::Instant::now(); 6 | let ret = f(); 7 | println!("time used {:?}", time::Instant::now().duration_since(t0)); 8 | 9 | ret 10 | } 11 | fn get_sum(input: &str) -> i32 { 12 | let re = Regex::new(r"mul\((\d+),(\d+)\)").unwrap(); 13 | re.captures_iter(input) 14 | .map(|cap| { 15 | let num1 = cap[1].parse::().unwrap(); 16 | let num2 = cap[2].parse::().unwrap(); 17 | num1 * num2 18 | }) 19 | .sum() 20 | } 21 | 22 | fn part_1() { 23 | println!("{}", get_sum(include_str!("input.txt"))); 24 | } 25 | 26 | fn part_2() { 27 | let re = Regex::new(r"don't\(\)[\s\S]*?do\(\)").unwrap(); 28 | let input = re.replace_all(include_str!("input.txt"), ""); 29 | println!("{}", get_sum(&input)); 30 | } 31 | 32 | fn main() { 33 | bench(part_1); 34 | bench(part_2); 35 | } 36 | -------------------------------------------------------------------------------- /2024/day07/code.py: -------------------------------------------------------------------------------- 1 | # pylint: disable=C0114,C0116,C0301,C0209,W1514,C0414 2 | 3 | from time import time as perf_counter 4 | from itertools import product 5 | from typing import Any 6 | import math 7 | 8 | from cProfile import run 9 | 10 | 11 | def profiler(method): 12 | def wrapper_method(*args: Any, **kwargs: Any) -> Any: 13 | t = perf_counter() 14 | ret = method(*args, **kwargs) 15 | print(f"Method {method.__name__} took : {perf_counter() - t:.3f} sec") 16 | return ret 17 | 18 | return wrapper_method 19 | 20 | 21 | def eval_right_to_left(nums, target, ops): 22 | s = nums[0] 23 | for i in range(len(ops)): 24 | if ops[i] == "+": 25 | s += nums[i+1] 26 | elif ops[i] == "*": 27 | s *= nums[i+1] 28 | elif ops[i] == "||": 29 | s = int(s * 10**int(math.log10(nums[i+1]) + 1) + nums[i+1]) 30 | if s > target: 31 | return False 32 | 33 | return s == target 34 | 35 | def does_match(target, nums, ops): 36 | for op in product(ops, repeat=len(nums) - 1): 37 | if eval_right_to_left(nums, target, op): 38 | return True 39 | return False 40 | 41 | 42 | @profiler 43 | def part1(): 44 | 45 | cals = [] 46 | with open("day07/input.txt") as f: 47 | for l in f: 48 | ps = l.strip().split(":") 49 | cals.append((int(ps[0]), list(map(int, ps[1].split())))) 50 | 51 | print(sum(v for v, nums in cals if does_match(v, nums, ["+", "*"]))) 52 | 53 | 54 | @profiler 55 | def part2(): 56 | 57 | cals = [] 58 | with open("day07/input.txt") as f: 59 | for l in f: 60 | ps = l.strip().split(":") 61 | cals.append((int(ps[0]), list(map(int, ps[1].split())))) 62 | 63 | print(sum(v for v, nums in cals if does_match(v, nums, ["+", "*", "||"]))) 64 | 65 | 66 | if __name__ == "__main__": 67 | part1() 68 | part2() 69 | run("part2()") 70 | -------------------------------------------------------------------------------- /2024/day10/main.rs: -------------------------------------------------------------------------------- 1 | use std::time::Instant; 2 | use std::collections::HashSet; 3 | 4 | fn bench(f: F) -> R 5 | where 6 | F: FnOnce() -> R, 7 | { 8 | let t0 = Instant::now(); 9 | let result = f(); // Call the function and store the result 10 | println!("time used: {:?}", Instant::now().duration_since(t0)); 11 | result // Return the result of the function 12 | } 13 | 14 | 15 | 16 | fn part_1() { 17 | let input = include_str!("input.txt"); // Use include_str! here 18 | } 19 | 20 | fn part_2() { 21 | let input = include_str!("input.txt"); // Use include_str! here 22 | } 23 | 24 | fn main() { 25 | bench(part_1); 26 | bench(part_2); 27 | } 28 | -------------------------------------------------------------------------------- /2024/day11/code.py: -------------------------------------------------------------------------------- 1 | # pylint: disable=C0114,C0116,C0301,C0209,W1514,C0414,C0200 2 | 3 | from time import time as perf_counter 4 | from typing import Any 5 | import os 6 | from collections import Counter 7 | 8 | input_file = os.path.join(os.path.dirname(__file__), "input.txt") 9 | # input_file = os.path.join(os.path.dirname(__file__), "test.txt") 10 | 11 | 12 | def profiler(method): 13 | def wrapper_method(*args: Any, **kwargs: Any) -> Any: 14 | t = perf_counter() 15 | ret = method(*args, **kwargs) 16 | print(f"Method {method.__name__} took : {perf_counter() - t:.3f} sec") 17 | return ret 18 | 19 | return wrapper_method 20 | 21 | 22 | def count_after_blinking(l_cnt, n): 23 | l_cnt = Counter(l_cnt) 24 | 25 | for _ in range(n): 26 | new_l = Counter() 27 | for s in l_cnt: 28 | if s == 0: 29 | new_l[1] += l_cnt[s] 30 | elif len(str(s)) % 2 == 0: 31 | num = str(s) 32 | n1 = int(str(num[:len(num)//2])) 33 | n2 = int(str(num[len(num)//2:])) 34 | new_l[n1] += l_cnt[s] 35 | new_l[n2] += l_cnt[s] 36 | 37 | else: 38 | new_l[s*2024] += l_cnt[s] 39 | 40 | l_cnt = new_l 41 | 42 | return sum(l_cnt.values()) 43 | 44 | 45 | @profiler 46 | def part_1(): 47 | with open(input_file) as f: 48 | l = list(map(int, f.read().split())) 49 | 50 | print(count_after_blinking(l, 25)) 51 | 52 | 53 | @profiler 54 | def part_2(): 55 | with open(input_file) as f: 56 | l = list(map(int, f.read().split())) 57 | 58 | print(count_after_blinking(l, 75)) 59 | 60 | 61 | if __name__ == "__main__": 62 | part_1() 63 | part_2() 64 | -------------------------------------------------------------------------------- /2024/day15/test_corner.txt: -------------------------------------------------------------------------------- 1 | ####### 2 | #.....# 3 | #.....# 4 | #.@O..# 5 | #..#O.# 6 | #...O.# 7 | #..O..# 8 | #.....# 9 | ####### 10 | 11 | >>v>^^^ -------------------------------------------------------------------------------- /2024/day19/code.py: -------------------------------------------------------------------------------- 1 | # pylint: disable=C0114,C0116,C0301,C0209,W1514,C0414,E0001 2 | 3 | from typing import Any 4 | import os 5 | from time import perf_counter_ns 6 | from functools import cache 7 | 8 | input_file = os.path.join(os.path.dirname(__file__), "input.txt") 9 | # input_file = os.path.join(os.path.dirname(__file__), "test.txt") 10 | 11 | 12 | def profiler(method): 13 | 14 | def wrapper_method(*args: Any, **kwargs: Any) -> Any: 15 | start_time = perf_counter_ns() 16 | ret = method(*args, **kwargs) 17 | stop_time = perf_counter_ns() - start_time 18 | time_len = min(9, ((len(str(stop_time))-1)//3)*3) 19 | time_conversion = {9: 'seconds', 6: 'milliseconds', 20 | 3: 'microseconds', 0: 'nanoseconds'} 21 | print(f"Method {method.__name__} took : { 22 | stop_time / (10**time_len)} {time_conversion[time_len]}") 23 | return ret 24 | 25 | return wrapper_method 26 | 27 | 28 | @cache 29 | def count_allowed(towel, patterns): 30 | combs = 0 31 | for p in patterns: 32 | if towel == p: 33 | combs += 1 34 | if towel.startswith(p): 35 | new_towel = towel.replace(p, "", 1) 36 | combs += count_allowed(new_towel, patterns) 37 | return combs 38 | 39 | 40 | @profiler 41 | def part_1(): 42 | with open(input_file) as f: 43 | ps = f.read().split("\n\n") 44 | 45 | allowed = frozenset(ps[0].split(", ")) 46 | towels = ps[1].split() 47 | 48 | print(sum(count_allowed(t, allowed) > 0 for t in towels)) 49 | 50 | 51 | @profiler 52 | def part_2(): 53 | with open(input_file) as f: 54 | ps = f.read().split("\n\n") 55 | 56 | allowed = frozenset(ps[0].split(", ")) 57 | towels = ps[1].split() 58 | 59 | print(sum(count_allowed(t, allowed) for t in towels)) 60 | 61 | 62 | if __name__ == "__main__": 63 | part_1() 64 | part_2() 65 | -------------------------------------------------------------------------------- /2024/day25/code.py: -------------------------------------------------------------------------------- 1 | # pylint: disable=C0114,C0116,C0301,C0209,W1514,C0414,E0001 2 | 3 | from typing import Any 4 | import os 5 | from time import perf_counter_ns 6 | from itertools import product 7 | 8 | input_file = os.path.join(os.path.dirname(__file__), "input.txt") 9 | # input_file = os.path.join(os.path.dirname(__file__), "test.txt") 10 | 11 | 12 | def profiler(method): 13 | 14 | def wrapper_method(*args: Any, **kwargs: Any) -> Any: 15 | start_time = perf_counter_ns() 16 | ret = method(*args, **kwargs) 17 | stop_time = perf_counter_ns() - start_time 18 | time_len = min(9, ((len(str(stop_time))-1)//3)*3) 19 | time_conversion = {9: 'seconds', 6: 'milliseconds', 20 | 3: 'microseconds', 0: 'nanoseconds'} 21 | print(f"Method {method.__name__} took : { 22 | stop_time / (10**time_len)} {time_conversion[time_len]}") 23 | return ret 24 | 25 | return wrapper_method 26 | 27 | 28 | def get_heights(d): 29 | return [sum(l[i] == "#" for l in d) for i in range(len(d[0]))] 30 | 31 | 32 | def does_fit(p): 33 | ks, ls = p 34 | return all(k+l <= 7 for k, l in zip(ks, ls)) 35 | 36 | 37 | @profiler 38 | def part_1(): 39 | key_heights = [] 40 | lock_heights = [] 41 | 42 | with open(input_file) as f: 43 | for block in f.read().split("\n\n"): 44 | lines = block.splitlines() 45 | if lines[0].count("#") > 0: 46 | lock_heights.append(get_heights(lines)) 47 | else: 48 | key_heights.append(get_heights(lines)) 49 | 50 | s = sum(does_fit(combination) 51 | for combination in product(key_heights, lock_heights)) 52 | print(s) 53 | 54 | 55 | if __name__ == "__main__": 56 | part_1() 57 | -------------------------------------------------------------------------------- /2024/day25/main.rs: -------------------------------------------------------------------------------- 1 | use std::iter::zip; 2 | use std::time::Instant; 3 | 4 | fn bench(f: F) -> R 5 | where 6 | F: FnOnce() -> R, 7 | { 8 | let t0 = Instant::now(); 9 | let result = f(); // Call the function and store the result 10 | println!("time used: {:?}", Instant::now().duration_since(t0)); 11 | result // Return the result of the function 12 | } 13 | 14 | fn get_heights(d: &[&str]) -> Vec { 15 | let mut ret = Vec::new(); 16 | let width = d[0].len(); 17 | 18 | for i in 0..width { 19 | let count = d 20 | .iter() 21 | .filter(|line| line.chars().nth(i) == Some('#')) 22 | .count(); 23 | ret.push(count); 24 | } 25 | ret 26 | } 27 | 28 | fn does_fit(p: (&[usize], &[usize])) -> bool { 29 | let (k, l) = p; 30 | zip(k, l).all(|(ki, li)| ki + li <= 7) 31 | } 32 | fn part_1() { 33 | let input_file = include_str!("input.txt"); 34 | let mut key_heights = Vec::new(); 35 | let mut lock_heights = Vec::new(); 36 | 37 | for block in input_file.split("\n\n") { 38 | let lines: Vec<&str> = block.lines().collect(); 39 | if lines[0].contains('#') { 40 | lock_heights.push(get_heights(&lines)); 41 | } else { 42 | key_heights.push(get_heights(&lines)); 43 | } 44 | } 45 | 46 | let mut s = 0; 47 | for key in &key_heights { 48 | for lock in &lock_heights { 49 | if does_fit((key, lock)) { 50 | s += 1; 51 | } 52 | } 53 | } 54 | 55 | println!("{}", s); 56 | } 57 | 58 | fn main() { 59 | bench(part_1); 60 | } 61 | -------------------------------------------------------------------------------- /2024/template/code.py: -------------------------------------------------------------------------------- 1 | # pylint: disable=C0114,C0116,C0301,C0209,W1514,C0414,E0001 2 | 3 | from typing import Any 4 | import os 5 | from time import perf_counter_ns 6 | 7 | input_file = os.path.join(os.path.dirname(__file__), "input.txt") 8 | # input_file = os.path.join(os.path.dirname(__file__), "test.txt") 9 | 10 | 11 | def profiler(method): 12 | 13 | def wrapper_method(*args: Any, **kwargs: Any) -> Any: 14 | start_time = perf_counter_ns() 15 | ret = method(*args, **kwargs) 16 | stop_time = perf_counter_ns() - start_time 17 | time_len = min(9, ((len(str(stop_time))-1)//3)*3) 18 | time_conversion = {9: 'seconds', 6: 'milliseconds', 19 | 3: 'microseconds', 0: 'nanoseconds'} 20 | print(f"Method {method.__name__} took : { 21 | stop_time / (10**time_len)} {time_conversion[time_len]}") 22 | return ret 23 | 24 | return wrapper_method 25 | 26 | 27 | @profiler 28 | def part_1(): 29 | with open(input_file) as _f: 30 | pass 31 | 32 | 33 | @profiler 34 | def part_2(): 35 | with open(input_file) as _f: 36 | pass 37 | 38 | 39 | if __name__ == "__main__": 40 | part_1() 41 | part_2() 42 | -------------------------------------------------------------------------------- /2024/template/main.rs: -------------------------------------------------------------------------------- 1 | use std::time::Instant; 2 | 3 | fn bench(f: F) -> R 4 | where 5 | F: FnOnce() -> R, 6 | { 7 | let t0 = Instant::now(); 8 | let result = f(); // Call the function and store the result 9 | println!("time used: {:?}", Instant::now().duration_since(t0)); 10 | result // Return the result of the function 11 | } 12 | 13 | fn part_1() { 14 | let input = include_str!("input.txt"); 15 | } 16 | 17 | fn part_2() { 18 | let input = include_str!("input.txt"); 19 | } 20 | 21 | fn main() { 22 | bench(part_1); 23 | bench(part_2); 24 | } 25 | -------------------------------------------------------------------------------- /2025/Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "advent_of_code_2025" 3 | version = "0.1.0" 4 | edition = "2021" 5 | 6 | [dependencies] 7 | regex="1.4.2" 8 | itertools = "0.13.0" 9 | 10 | [dev-dependencies] 11 | criterion = "0.4" 12 | 13 | [[bin]] 14 | name="template" 15 | path="template/mod.rs" 16 | 17 | [[bench]] 18 | name = "benches" 19 | harness = false 20 | path="benches.rs" -------------------------------------------------------------------------------- /2025/benches.rs: -------------------------------------------------------------------------------- 1 | use criterion::{criterion_group, criterion_main, Criterion}; 2 | 3 | mod template; 4 | 5 | fn template_benchmark(c: &mut Criterion) { 6 | c.bench_function("template_p1", |b| b.iter(|| template::part_1())); 7 | c.bench_function("template_p2", |b| b.iter(|| template::part_2())); 8 | } 9 | 10 | criterion_group!(benches, template_benchmark); 11 | criterion_main!(benches); 12 | -------------------------------------------------------------------------------- /2025/template/code.py: -------------------------------------------------------------------------------- 1 | # pylint: disable=C0114,C0116,C0301,C0209,W1514,C0414,E0001 2 | 3 | from typing import Any 4 | import os 5 | from time import perf_counter_ns 6 | 7 | input_file = os.path.join(os.path.dirname(__file__), "input.txt") 8 | # input_file = os.path.join(os.path.dirname(__file__), "test.txt") 9 | 10 | 11 | def profiler(method): 12 | 13 | def wrapper_method(*args: Any, **kwargs: Any) -> Any: 14 | start_time = perf_counter_ns() 15 | ret = method(*args, **kwargs) 16 | stop_time = perf_counter_ns() - start_time 17 | time_len = min(9, ((len(str(stop_time))-1)//3)*3) 18 | time_conversion = {9: 'seconds', 6: 'milliseconds', 19 | 3: 'microseconds', 0: 'nanoseconds'} 20 | print(f"Method {method.__name__} took : { 21 | stop_time / (10**time_len)} {time_conversion[time_len]}") 22 | return ret 23 | 24 | return wrapper_method 25 | 26 | 27 | @profiler 28 | def part_1(): 29 | with open(input_file) as _f: 30 | pass 31 | 32 | 33 | @profiler 34 | def part_2(): 35 | with open(input_file) as _f: 36 | pass 37 | 38 | 39 | if __name__ == "__main__": 40 | part_1() 41 | part_2() 42 | -------------------------------------------------------------------------------- /2025/template/mod.rs: -------------------------------------------------------------------------------- 1 | use std::time::Instant; 2 | 3 | fn bench(f: F) -> R 4 | where 5 | F: FnOnce() -> R, 6 | { 7 | let t0 = Instant::now(); 8 | let result = f(); // Call the function and store the result 9 | println!("time used: {:?}", Instant::now().duration_since(t0)); 10 | result // Return the result of the function 11 | } 12 | 13 | pub fn part_1() { 14 | let input = include_str!("input.txt"); 15 | let a = 5*4; 16 | } 17 | 18 | pub fn part_2() { 19 | let input = include_str!("input.txt"); 20 | let a = 5*4; 21 | } 22 | 23 | fn main() { 24 | bench(part_1); 25 | bench(part_2); 26 | } 27 | -------------------------------------------------------------------------------- /CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required (VERSION 3.8) 2 | 3 | project(AoC) 4 | 5 | #add_subdirectory(2018) 6 | add_subdirectory(2019) 7 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | This is free and unencumbered software released into the public domain. 2 | 3 | Anyone is free to copy, modify, publish, use, compile, sell, or 4 | distribute this software, either in source code form or as a compiled 5 | binary, for any purpose, commercial or non-commercial, and by any 6 | means. 7 | 8 | In jurisdictions that recognize copyright laws, the author or authors 9 | of this software dedicate any and all copyright interest in the 10 | software to the public domain. We make this dedication for the benefit 11 | of the public at large and to the detriment of our heirs and 12 | successors. We intend this dedication to be an overt act of 13 | relinquishment in perpetuity of all present and future rights to this 14 | software under copyright law. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 17 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 18 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 19 | IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR 20 | OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 21 | ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR 22 | OTHER DEALINGS IN THE SOFTWARE. 23 | 24 | For more information, please refer to 25 | 26 | in that scope software refers to only the code, any inputs and test sample are not subjected to the same license terms and are not for use without the explicit premission of the trademark owner in the USA of adventofcode 27 | --------------------------------------------------------------------------------