Optimise Day 10
[advent-of-code-2019.git] / day10 / common.sh
index db5c6b9df6a70d4b4434ed628726f0bd15c0cd1d..4f961b6caf43f9034f8f3a1120ff5c5aaf8360f3 100644 (file)
@@ -1,3 +1,42 @@
+declare -A asteroids
+declare __asteroids_grid_height
+declare __asteroids_grid_width
+
+get_grid_height() {
+    echo $__asteroids_grid_height
+}
+
+get_grid_width() {
+    echo $__asteroids_grid_width
+}
+
+read_file() {
+    filename="$1"
+
+    if [ ! -e "$filename" ]; then
+        echo "Couldn't find file: $filename"
+        exit 2
+    fi
+
+    exec 3<"$filename"
+    unset asteroids
+    declare -g -A asteroids
+
+    __asteroids_grid_height=0
+    __asteroids_grid_width=0
+
+    while read -u 3 line; do
+        __asteroids_grid_width=${#line}
+        for (( a=0; a<${#line}; a++ )); do
+            char=${line:$a:1}
+            if [ "${char}" == "#" ]; then
+                asteroids[$a,$__asteroids_grid_height]=0
+            fi
+        done
+        __asteroids_grid_height=$((__asteroids_grid_height+1))
+    done
+}
+
 get_vector() {
     local x1=$1
     local y1=$2
@@ -22,4 +61,68 @@ get_asteroids_vector() {
     get_vector $x1 $y1 $x2 $y2
 }
 
+get_angle() {
+    local a1=$1
+    local a2=$2
+
+    local vector=$(get_asteroids_vector $a1 $a2)
+    local move_x=${vector%,*}
+    local move_y=${vector#*,}
+
+    val="$(calc -p 'round(((90 + ((180/pi()) * atan2('$move_y','$move_x'))) % 360) * 100000000) / 100000000')"
+    echo "$val"
+}
+
+get_closest_asteroid() {
+    local asteroids=$1
+
+    local IFS="|"
+    local min_dist=-1
+    local nearest_asteroid=
+    local x=0
+    local y=0
+
+    for asteroid in $asteroids; do
+        vector=$(get_asteroids_vector $our_asteroid $asteroid)
+        x=${vector%,*}
+        y=${vector#*,}
+        # use absolute numbers for length calculation!
+        x=${x#-}
+        y=${y#-}
+
+        distance=$((x+y))
+        if [ $distance -lt $min_dist -o $min_dist -eq -1 ]; then
+            min_dist=$distance
+            nearest_asteroid=$asteroid
+        fi
+    done
+
+    echo $nearest_asteroid
+}
+
+remove_asteroid_from_string() {
+    local asteroids=$1
+    local asteroid=$2
+    local new_asteroids=
+    local a
+
+    local IFS="|"
+    local seperator=""
+
+    for a in $asteroids; do
+        if [ "$a" != "$asteroid" ]; then
+            new_asteroids+="${seperator}$a"
+        fi
+        if [ "x$new_asteroids" != "x" ]; then
+            seperator="|"
+        fi
+    done
+
+    echo "$new_asteroids"
+}
+
+get_angles_list() {
+    local -n __asteroid_angles=$1
+    printf "%s\n" "${!__asteroid_angles[@]}" | sort -g
+}