Skip to content
GitLab
Explore
Sign in
Primary navigation
Search or go to…
Project
A
Advent of Coding
Manage
Activity
Members
Labels
Plan
Issues
Issue boards
Milestones
Wiki
Code
Merge requests
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Snippets
Build
Pipelines
Jobs
Pipeline schedules
Artifacts
Deploy
Releases
Package registry
Container registry
Model registry
Operate
Environments
Terraform modules
Monitor
Incidents
Service Desk
Analyze
Value stream analytics
Contributor analytics
CI/CD analytics
Repository analytics
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
Community forum
Contribute to GitLab
Provide feedback
Keyboard shortcuts
?
Snippets
Groups
Projects
Show more breadcrumbs
Christopher Bohn
Advent of Coding
Commits
f0f55486
Commit
f0f55486
authored
2 years ago
by
Christopher Bohn
Browse files
Options
Downloads
Patches
Plain Diff
Completed 2022 Day 18
parent
644f2198
No related branches found
No related tags found
No related merge requests found
Changes
2
Show whitespace changes
Inline
Side-by-side
Showing
2 changed files
2022/README.md
+30
-0
30 additions, 0 deletions
2022/README.md
2022/src/main/java/edu/unl/cse/bohn/year2022/Day18.java
+177
-0
177 additions, 0 deletions
2022/src/main/java/edu/unl/cse/bohn/year2022/Day18.java
with
207 additions
and
0 deletions
2022/README.md
+
30
−
0
View file @
f0f55486
...
...
@@ -654,9 +654,39 @@ No. That solves the memory problem but not the time problem.
Even if we could process 4 billion rocks per second (which we can't) then it would take a little over 4 minutes to
process 1 trillion rocks, and AOC solutions shouldn't take that long.
There is almost certainly a cycle (with a period that is a multiple of both the number of rocks and the length of the
jet string?) -- if we can detect the cycle then we can determine the height as (height of prefix) +
(number of cycles)
*
(height of a cycle) + (height of suffix). Maybe later.
...
## Day 18
-
[
The problem
](
https://adventofcode.com/2022/day/18
)
-
[
The solution
](
src/main/java/edu/unl/cse/bohn/year2022/Day18.java
)
### Part 1
The subproblems are
-
Parse the input to determine where each cube is in space
-
For each cube, determine which faces are adjacent to another cube
-
Count the number of faces that are not adjacent to another cube
Determining whether a face is adjacent to another cube should be straight-forward.
Given axes
*i*
,
*j*
, and
*k*
, cube
*c1*
is adjacent to cube
*c2*
iff wlog
*c1.i*
=
*c2.i*
and
*c1.j*
=
*c2.j*
and
*c1.k*
=
*c2.k*
± 1.
### Part 2
We need to determine how many cavities are present in the droplet.
We can determine that by eliminating everything that is
*not*
a cavity.
If we consider a bounding box, then every cube is either:
-
Lava, as computed in part 1
-
Exterior air, which has no lava between it and the box's bound in at least one direction
-
A cavity
## Day 19
(coming soon)
This diff is collapsed.
Click to expand it.
2022/src/main/java/edu/unl/cse/bohn/year2022/Day18.java
0 → 100644
+
177
−
0
View file @
f0f55486
package
edu.unl.cse.bohn.year2022
;
import
edu.unl.cse.bohn.Puzzle
;
import
java.util.Arrays
;
import
java.util.HashSet
;
import
java.util.List
;
import
java.util.Set
;
import
java.util.stream.IntStream
;
@SuppressWarnings
(
"unused"
)
public
class
Day18
extends
Puzzle
{
@SuppressWarnings
(
"CommentedOutCode"
)
public
Day18
(
boolean
isProductionReady
)
{
super
(
isProductionReady
);
// sampleData = """
// 1,1,1
// 2,1,1""";
sampleData
=
"""
2,2,2
1,2,2
3,2,2
2,1,2
2,3,2
2,2,1
2,2,3
2,2,4
2,2,6
1,2,5
3,2,5
2,1,5
2,3,5"""
;
}
@Override
public
long
computePart1
(
List
<
String
>
data
)
{
for
(
String
description
:
data
)
{
new
Cube
(
description
);
}
for
(
Cube
cube1
:
Cube
.
lava
)
{
for
(
Cube
cube2
:
Cube
.
lava
)
{
cube1
.
checkIfAdjacentTo
(
cube2
);
}
}
return
Cube
.
lava
.
stream
().
mapToLong
(
Cube:
:
countExposedFaces
).
sum
();
}
@Override
public
long
computePart2
(
List
<
String
>
data
)
{
// assume (correctly) that lava has already been created
int
upperBound
=
Cube
.
maximumLength
+
2
;
// plenty
for
(
int
i
=
0
;
i
<
upperBound
;
i
++)
{
for
(
int
j
=
0
;
j
<
upperBound
;
j
++)
{
for
(
int
k
=
0
;
k
<
upperBound
;
k
++)
{
new
Cube
(
i
,
j
,
k
);
}
}
}
Cube
.
removeExteriorAir
();
for
(
Cube
lavaCube
:
Cube
.
lava
)
{
for
(
Cube
airCube
:
Cube
.
air
)
{
lavaCube
.
checkIfAdjacentTo
(
airCube
);
}
}
return
Cube
.
lava
.
stream
().
mapToLong
(
Cube:
:
countExposedFaces
).
sum
();
}
private
static
class
Cube
{
public
static
final
Set
<
Cube
>
lava
=
new
HashSet
<>();
public
static
final
Set
<
Cube
>
air
=
new
HashSet
<>();
static
int
maximumLength
=
Integer
.
MIN_VALUE
;
private
final
int
[]
coordinates
;
private
final
boolean
[]
faceIsExposed
;
public
Cube
(
String
lavaDescription
)
{
// use for lava
coordinates
=
Arrays
.
stream
(
lavaDescription
.
split
(
","
)).
mapToInt
(
Integer:
:
parseInt
).
toArray
();
faceIsExposed
=
new
boolean
[]{
true
,
true
,
true
,
true
,
true
,
true
};
maximumLength
=
Math
.
max
(
maximumLength
,
Arrays
.
stream
(
coordinates
).
max
().
orElseThrow
());
air
.
remove
(
this
);
lava
.
add
(
this
);
}
public
Cube
(
int
x
,
int
y
,
int
z
)
{
// use for air
coordinates
=
new
int
[]{
x
,
y
,
z
};
faceIsExposed
=
new
boolean
[]{
true
,
true
,
true
,
true
,
true
,
true
};
if
(!
lava
.
contains
(
this
))
{
air
.
add
(
this
);
}
}
public
static
void
removeExteriorAir
()
{
Set
<
Cube
>
exteriorAir
=
new
HashSet
<>();
for
(
Cube
airCube
:
air
)
{
for
(
Cube
lavaCube
:
lava
)
{
if
(
airCube
.
isAlignedInTwoDimensionsWith
(
lavaCube
,
1
,
2
)
&&
airCube
.
distanceInOneDimension
(
lavaCube
,
0
)
!=
0
)
{
airCube
.
faceIsExposed
[
airCube
.
distanceInOneDimension
(
lavaCube
,
0
)
<
0
?
0
:
1
]
=
false
;
}
if
(
airCube
.
isAlignedInTwoDimensionsWith
(
lavaCube
,
0
,
2
)
&&
airCube
.
distanceInOneDimension
(
lavaCube
,
1
)
!=
0
)
{
airCube
.
faceIsExposed
[
2
+
(
airCube
.
distanceInOneDimension
(
lavaCube
,
1
)
<
0
?
0
:
1
)]
=
false
;
}
if
(
airCube
.
isAlignedInTwoDimensionsWith
(
lavaCube
,
0
,
1
)
&&
airCube
.
distanceInOneDimension
(
lavaCube
,
2
)
!=
0
)
{
airCube
.
faceIsExposed
[
4
+
(
airCube
.
distanceInOneDimension
(
lavaCube
,
2
)
<
0
?
0
:
1
)]
=
false
;
}
}
if
(
airCube
.
countExposedFaces
()
>
0
)
{
exteriorAir
.
add
(
airCube
);
}
}
air
.
removeAll
(
exteriorAir
);
// if we stopped now, then air in twisty passages would be treated as cavities
// any air that is adjacent to exterior air must also be exterior air
Set
<
Cube
>
newlyDiscoveredExteriorAir
;
do
{
newlyDiscoveredExteriorAir
=
new
HashSet
<>();
for
(
Cube
cavityCube
:
air
)
{
for
(
Cube
exteriorCube
:
exteriorAir
)
{
if
(
cavityCube
.
checkIfAdjacentTo
(
exteriorCube
))
{
newlyDiscoveredExteriorAir
.
add
(
cavityCube
);
}
}
}
exteriorAir
.
addAll
(
newlyDiscoveredExteriorAir
);
air
.
removeAll
(
newlyDiscoveredExteriorAir
);
}
while
(!
newlyDiscoveredExteriorAir
.
isEmpty
());
}
private
int
distanceInOneDimension
(
Cube
other
,
int
dimension
)
{
return
other
.
coordinates
[
dimension
]
-
this
.
coordinates
[
dimension
];
}
private
boolean
isAlignedInTwoDimensionsWith
(
Cube
other
,
int
dimension1
,
int
dimension2
)
{
return
distanceInOneDimension
(
other
,
dimension1
)
==
0
&&
distanceInOneDimension
(
other
,
dimension2
)
==
0
;
}
@SuppressWarnings
(
"UnusedReturnValue"
)
private
boolean
checkIfAdjacentTo
(
Cube
other
)
{
if
(
isAlignedInTwoDimensionsWith
(
other
,
1
,
2
)
&&
Math
.
abs
(
distanceInOneDimension
(
other
,
0
))
==
1
)
{
faceIsExposed
[(
1
+
distanceInOneDimension
(
other
,
0
))
/
2
]
=
false
;
return
true
;
}
if
(
isAlignedInTwoDimensionsWith
(
other
,
0
,
2
)
&&
Math
.
abs
(
distanceInOneDimension
(
other
,
1
))
==
1
)
{
faceIsExposed
[
2
+
(
1
+
distanceInOneDimension
(
other
,
1
))
/
2
]
=
false
;
return
true
;
}
if
(
isAlignedInTwoDimensionsWith
(
other
,
0
,
1
)
&&
Math
.
abs
(
distanceInOneDimension
(
other
,
2
))
==
1
)
{
faceIsExposed
[
4
+
(
1
+
distanceInOneDimension
(
other
,
2
))
/
2
]
=
false
;
return
true
;
}
return
false
;
}
private
long
countExposedFaces
()
{
return
IntStream
.
range
(
0
,
faceIsExposed
.
length
).
filter
(
i
->
faceIsExposed
[
i
]).
count
();
}
@Override
public
boolean
equals
(
Object
other
)
{
if
(
this
==
other
)
return
true
;
if
(!(
other
instanceof
Cube
cube
))
return
false
;
return
Arrays
.
equals
(
coordinates
,
cube
.
coordinates
);
}
@Override
public
int
hashCode
()
{
return
Arrays
.
hashCode
(
coordinates
);
}
}
}
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment