cem 0.1.3 → 0.1.4

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 014d136cae33adc2f8715b45c280fb55f11242f7c70940d040bce1e545b97e7b
4
- data.tar.gz: fbbd2a832bbf96fa5f18c48557b4f081902657faeb57106e6a5227d73f409952
3
+ metadata.gz: a12790b597c9fd5c63fc14b855b964d32aeda5f968d612806e8d80697bbb37c4
4
+ data.tar.gz: 0acf18fd6f7dafe94553e55dca0e89c3304066b5ec85d1413187eb4afe6d7774
5
5
  SHA512:
6
- metadata.gz: c3a7fa8ba025117c5035abe10a58004d03d3db9741cd1b1c10d22d976112b7c94ad9e0807d0bf930d411768060ac8eb6c5a34718125fac8be1eb3c2dc5103ea3
7
- data.tar.gz: 2ac9b662fe5ef2aaf459d5c93dd7a5da5cbecb23260ae21bc201b75a294ec0defe121cbf39ccd9978af2595c9c116e756aac6edf68be64e4986923474ba9652a
6
+ metadata.gz: 4b8f6e808871a8b4197126f576940ca6a98daff481339ab4f9830316fecf2b4cab2d3bf7000b18ed39276731d2a431408dccfd799fc4ec784ac3901ade4f27eb
7
+ data.tar.gz: 142741554b2f214d0af5cbffbc0ecb9860ef9e7870697863af38eab01c3a811b3ac459cad093cc1b372962d7ba224beeb8c86a2bd58dc7f96c460e93bcbb4c43
data/.gitignore CHANGED
@@ -54,4 +54,5 @@ Gemfile.lock
54
54
  .rvmrc
55
55
 
56
56
  # Used by RuboCop. Remote config files pulled in from inherit_from directive.
57
- # .rubocop-https?--*
57
+ # .rubocop-https?--
58
+ .idea/
@@ -35,8 +35,8 @@ Gem::Specification.new do |spec|
35
35
  spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
36
36
  spec.require_paths = ["lib"]
37
37
 
38
- spec.add_development_dependency "bundler", "~> 1.17"
39
- spec.add_development_dependency "rake", "~> 10.0"
38
+ spec.add_development_dependency "bundler", "~> 2.1" # Was 1.17
39
+ spec.add_development_dependency "rake", "~> 13.0" # Was: 10.0
40
40
  spec.add_development_dependency "rspec", "~> 3.0"
41
41
 
42
42
  spec.add_runtime_dependency 'flammarion', '~> 0.3'
@@ -0,0 +1,13 @@
1
+
2
+ #
3
+ # https://adventofcode.com/2018/day/1 Part 1
4
+ #
5
+ # Does not use any cem functions \o/
6
+ #
7
+
8
+ result = 0
9
+ File.read("inputs/day1_input.txt").each_line { |line|
10
+ result += line.to_i
11
+ }
12
+
13
+ puts result
@@ -0,0 +1,30 @@
1
+
2
+ #
3
+ # https://adventofcode.com/2018/day/1 Part 2
4
+ #
5
+ # Does not use any cem functions \o/ but did you know:
6
+ #
7
+ # - Set provides #[] as a class method: Set[1,2,3] is the same as Set.new() and then Set.add(...)
8
+ # - Set provides #add?() to add and check if the object added was already in the Set (returns nil in case).
9
+ #
10
+ # For example: Set[0,1].add?(1) => nil
11
+ #
12
+
13
+ require 'set'
14
+
15
+ cur = 0
16
+ seen_before = Set[0]
17
+
18
+ while true
19
+ File.read("inputs/day1_input.txt").each_line { |line|
20
+
21
+ cur += line.to_i
22
+
23
+ if !seen_before.add?(cur)
24
+ puts cur
25
+ exit
26
+ end
27
+ }
28
+ end
29
+
30
+ # Unreachable!
@@ -0,0 +1,20 @@
1
+
2
+ #
3
+ # https://adventofcode.com/2018/day/2
4
+ #
5
+ # Does not use any cem functions \o/
6
+ #
7
+ twice = 0
8
+ thrice = 0
9
+
10
+ chars = [*'a'..'z', *'A'..'Z']
11
+
12
+ File.read("inputs/day2_input.txt").each_line { |l|
13
+
14
+ twice += 1 if chars.any? { |c| l.count(c) == 2 }
15
+ thrice += 1 if chars.any? { |c| l.count(c) == 3 }
16
+
17
+ }
18
+
19
+ puts "1st star: #{twice * thrice}"
20
+
@@ -0,0 +1,27 @@
1
+
2
+ #
3
+ # https://adventofcode.com/2018/day/2 part 2
4
+ #
5
+ # Does not use any cem functions \o/
6
+
7
+ previous = ''
8
+ File.readlines("inputs/day2_input.txt").sort.each { |l|
9
+
10
+ mismatch = 0
11
+ s = ''
12
+ if previous != ''
13
+ l.split("").each_with_index { |c, i|
14
+ if previous[i] != c
15
+ mismatch += 1
16
+ else
17
+ s += c
18
+ end
19
+ }
20
+ end
21
+
22
+ if mismatch == 1
23
+ puts s
24
+ end
25
+
26
+ previous = l
27
+ }
@@ -0,0 +1,71 @@
1
+
2
+ #
3
+ # https://adventofcode.com/2018/day/3 part 1 and 2
4
+ #
5
+ # Demonstrates: Point2D, min(a,b), Array::with_progress
6
+ #
7
+ # Areas for improvement: Rect intersection
8
+
9
+ require 'set'
10
+ require 'cem'
11
+
12
+ claims = []
13
+ intersections = Set.new
14
+ doesIntersect = Set.new
15
+
16
+ Claim = Struct.new("Claim", :x, :y, :width, :height, :claimId)
17
+
18
+ File.readlines("inputs/day3_input.txt").with_progress.each { |l|
19
+
20
+ if l =~ /^\#(\d+) \@ (\d+),(\d+)\: (\d+)x(\d+)$/
21
+
22
+ claim = Claim.new($2.to_i, $3.to_i, $4.to_i, $5.to_i, $1.to_i)
23
+
24
+ claims.each { |other|
25
+
26
+ x = claim.x
27
+ y = claim.y
28
+ w = claim.width
29
+ h = claim.height
30
+
31
+ x2 = other.x
32
+ y2 = other.y
33
+ w2 = other.width
34
+ h2 = other.height
35
+
36
+ if x2 < x
37
+ x, x2 = x2, x
38
+ w, w2 = w2, w
39
+ end
40
+
41
+ if y2 < y
42
+ y, y2 = y2, y
43
+ h, h2 = h2, h
44
+ end
45
+
46
+ # puts "#{claim} - #{other}"
47
+
48
+ if x + w >= x2 && y + h >= y2
49
+
50
+ width = min(x2 + w2, x + w)
51
+ height = min(y2 + h2, y + h)
52
+
53
+ doesIntersect.add(other)
54
+ doesIntersect.add(claim)
55
+
56
+ for a in x2...width
57
+ for b in y2...height
58
+ # puts "#{a} #{b}"
59
+ intersections.add(Point2D.new(a,b))
60
+ end
61
+ end
62
+
63
+ end
64
+ }
65
+
66
+ claims << claim
67
+ end
68
+ }
69
+
70
+ puts "Part 1: #{intersections.size}"
71
+ puts "Part 2: #{claims.to_set.subtract(doesIntersect).first.claimId}"
@@ -0,0 +1,46 @@
1
+
2
+ #
3
+ # https://adventofcode.com/2018/day/4
4
+ #
5
+ # Does not use any cem functions \o/
6
+
7
+ Guard = Struct.new("Guard", :id, :total, :minutes)
8
+
9
+ guards = {}
10
+ guard = nil
11
+ asleep = nil
12
+
13
+ File.readlines("inputs/day4_input.txt", chomp: true).sort.each { |l|
14
+
15
+ if l =~ /Guard \#(\d+) begins shift$/
16
+
17
+ id = $1.to_i
18
+ guard = guards[id] ||= Guard.new(id, 0, [0] * 60)
19
+
20
+ elsif / 00:(?<minute>\d+)\] falls asleep$/ =~ l
21
+
22
+ asleep = minute.to_i
23
+
24
+ elsif l =~ / 00:(\d+)\] wakes up$/
25
+
26
+ awake = $1.to_i
27
+
28
+ guard.total += awake - asleep
29
+ (asleep...awake).each { |min|
30
+ guard.minutes[min] += 1
31
+ }
32
+
33
+ end
34
+ }
35
+
36
+ guard = (guards.values.sort_by {|g| g.total}).last
37
+ puts "Part1: #{guard.id * guard.minutes.each_with_index.max[1]}"
38
+
39
+ guard = (guards.values.sort_by {|g| g.minutes.each_with_index.max[0] }).last
40
+ puts "Part2: #{guard.id * guard.minutes.each_with_index.max[1]}"
41
+
42
+
43
+
44
+
45
+
46
+
@@ -0,0 +1,23 @@
1
+
2
+ #
3
+ # https://adventofcode.com/2018/day/5 Part 1
4
+ #
5
+ # Does not use any cem functions \o/ but did you know:
6
+ #
7
+ # - String#swapcase turns "Hello" into "hELLO"?
8
+ #
9
+
10
+ out = []
11
+
12
+ File.read("inputs/day5_input.txt").each_char { |c|
13
+
14
+ if out.empty? || out.last != c.swapcase
15
+ out << c
16
+ else
17
+ out.pop
18
+ end
19
+
20
+ }
21
+
22
+ puts out.join.size
23
+
@@ -0,0 +1,29 @@
1
+
2
+ #
3
+ # https://adventofcode.com/2018/day/5 Part 2
4
+ #
5
+ # Does not use any cem functions \o/ but did you know:
6
+ #
7
+ # - String#swapcase turns a Hello into hELLO?
8
+ # - Regex support 'i' for insensitive matches?
9
+ #
10
+
11
+ File.readlines("inputs/day5_input.txt").each { |line|
12
+
13
+ puts [*'a'..'z'].map { |delete|
14
+
15
+ out = []
16
+
17
+ line.gsub(/#{delete}/i, '').each_char { |c|
18
+ if out.empty? || out.last != c.swapcase
19
+ out << c
20
+ else
21
+ out.pop
22
+ end
23
+ }
24
+
25
+ out.join.size
26
+ }.min
27
+ }
28
+
29
+
@@ -0,0 +1,53 @@
1
+
2
+ #
3
+ # https://adventofcode.com/2018/day/6 Part 1 and 2
4
+ #
5
+ # Uses Point2D from cem
6
+
7
+ require 'cem'
8
+
9
+ out = {}
10
+ points = []
11
+ largestRegion = 0
12
+
13
+ File.readlines("inputs/day6_input.txt", chomp: true).each { |line|
14
+ if line =~ /^(\d+), (\d+)$/
15
+ v1 = $1.to_i
16
+ v2 = $2.to_i
17
+
18
+ points << Point2D.new(v1, v2)
19
+ end
20
+ }
21
+
22
+ minX, maxX = points.map { |p| p.x }.minmax
23
+ minY, maxY = points.map { |p| p.y }.minmax
24
+
25
+ (minX..maxX).each { |x|
26
+ (minY..maxY).each { |y|
27
+
28
+ coord = Point2D.new(x,y)
29
+
30
+ nearest = points.group_by { |p| p.manhattan(coord) }.min_by { |k,v| k }
31
+
32
+ # puts nearest.inspect
33
+ if nearest.last.size == 1
34
+ (out[nearest.last.first] ||= []) << coord
35
+ end
36
+
37
+ if points.sum { |p| p.manhattan(coord) } < 10000
38
+ largestRegion += 1
39
+ end
40
+ }
41
+ }
42
+
43
+ puts "Part 1"
44
+ puts out.max_by { |k,v|
45
+ if v.select { |coord| (coord.x == maxX || coord.x == minX || coord.y == maxY || coord.y == minY) }.empty?
46
+ v.size
47
+ else
48
+ 0 # don't care about infinite
49
+ end
50
+ }.last.size
51
+
52
+ puts "Part 2"
53
+ puts largestRegion
@@ -0,0 +1,110 @@
1
+
2
+ #
3
+ # https://adventofcode.com/2018/day/7 part 1 and 2
4
+ #
5
+ # Does not use any cem functions \o/
6
+ #
7
+
8
+ require 'set'
9
+
10
+ Worker = Struct.new("Worker", :readyAt, :workingOn)
11
+
12
+ def read
13
+ input = File.readlines("inputs/day7_input.txt", chomp: true)
14
+
15
+ @edges = {}
16
+ @chars = Set.new
17
+
18
+ input.each { |line|
19
+
20
+ if line =~ /^Step (.+) must be finished before step (.+) can begin.$/
21
+ to = $1
22
+ from = $2
23
+
24
+ @chars.add(to)
25
+ @chars.add(from)
26
+
27
+ (@edges[from] ||= []) << to
28
+ end
29
+
30
+ @chars.each { |c| @edges[c] ||= [] }
31
+ }
32
+ end
33
+
34
+ def anyWorkerReady
35
+ return @idleWorkers.size > 0
36
+ end
37
+
38
+ def availableWork
39
+ return @chars.select { |c| @edges.include?(c) && @edges[c].size == 0 }.sort
40
+ end
41
+
42
+ def anyWorkAvailable
43
+ return availableWork.size > 0
44
+ end
45
+
46
+ def timeStep
47
+
48
+ puts "#{@timeNow}: #{@busyWorkers.inspect}" if $DEBUG
49
+
50
+ w = @busyWorkers.min_by { |w| w.readyAt }
51
+ @timeNow = w.readyAt
52
+ @busyWorkers -= [w]
53
+ @idleWorkers += [w]
54
+
55
+ c = w.workingOn
56
+
57
+ @result += c
58
+
59
+ @edges.update(@edges) { |k,v|
60
+ v - [c]
61
+ }
62
+ end
63
+
64
+ def scheduleWork
65
+
66
+ nextTask = availableWork.first
67
+
68
+ w = @idleWorkers.pop
69
+ @busyWorkers += [w]
70
+ w.workingOn = nextTask
71
+ w.readyAt = @timeNow + 61 + nextTask.ord - 'A'.ord
72
+ @edges.delete(nextTask)
73
+
74
+ puts "Scheduling #{nextTask} to be ready at #{w.readyAt}" if $DEBUG
75
+
76
+ end
77
+
78
+ def process(parallelism)
79
+
80
+ read()
81
+
82
+ @timeNow = 0
83
+ @result = ""
84
+
85
+ @busyWorkers = []
86
+ @idleWorkers = []
87
+ parallelism.times { @idleWorkers << Worker.new(0, '') }
88
+
89
+ loop do
90
+
91
+ while (!anyWorkerReady || !anyWorkAvailable) && @busyWorkers.size > 0
92
+ timeStep
93
+ end
94
+
95
+ if !anyWorkAvailable
96
+ break
97
+ end
98
+
99
+ scheduleWork
100
+
101
+ end
102
+
103
+ puts "Parallelism: #{parallelism}"
104
+ puts @result
105
+ puts @timeNow
106
+
107
+ end
108
+
109
+ process(1)
110
+ process(5)