- commit
- 557e065dfb9cbb60a158ee15cd4809662a302f9e
- parent
- 387fe63045a164a7ed2436df870e112ceba8e28d
- Author
- Tobias Bengfort <tobias.bengfort@posteo.de>
- Date
- 2024-01-03 15:43
Revert "foo" This reverts commit 387fe63045a164a7ed2436df870e112ceba8e28d.
Diffstat
D | 2023/24/rational.rs | 113 | ------------------------------------------------------------ |
D | 2023/24/solution.rs | 158 | ------------------------------------------------------------ |
2 files changed, 0 insertions, 271 deletions
diff --git a/2023/24/rational.rs b/2023/24/rational.rs
@@ -1,113 +0,0 @@1 -1 use std::fmt::Debug;2 -1 use std::fmt::Display;3 -1 use std::fmt::Formatter;4 -1 use std::ops::Add;5 -1 use std::ops::Div;6 -1 use std::ops::Mul;7 -1 use std::ops::Neg;8 -1 use std::ops::Sub;9 -110 -1 fn gcd(a: i128, b: i128) -> i128 {11 -1 let mut x1 = a.abs().max(b.abs());12 -1 let mut x2 = a.abs().min(b.abs());13 -114 -1 while x2 > 0 {15 -1 (x1, x2) = (x2, x1 % x2);16 -1 }17 -118 -1 return x1;19 -1 }20 -121 -1 #[derive(Clone, Copy)]22 -1 pub struct Rational {23 -1 pub numerator: i128,24 -1 pub denominator: i128,25 -1 }26 -127 -1 impl Rational {28 -1 fn new(numerator: i128, denominator: i128) -> Self {29 -1 let mut a = gcd(numerator, denominator);30 -1 if denominator < 0 {31 -1 a = -a;32 -1 }33 -1 return Self {34 -1 numerator: numerator / a,35 -1 denominator: denominator / a,36 -1 };37 -1 }38 -139 -1 pub fn n(i: i128) -> Self {40 -1 return Self::new(i, 1);41 -1 }42 -143 -1 pub fn as_f64(self) -> f64 {44 -1 return self.numerator as f64 / self.denominator as f64;45 -1 }46 -1 }47 -148 -1 impl Display for Rational {49 -1 fn fmt(&self, f: &mut Formatter<'_>) -> Result<(), std::fmt::Error> {50 -1 if self.denominator == 1 {51 -1 return write!(f, "{}", self.numerator);52 -1 } else {53 -1 return write!(f, "{}/{}", self.numerator, self.denominator);54 -1 }55 -1 }56 -1 }57 -158 -1 impl Debug for Rational {59 -1 fn fmt(&self, f: &mut Formatter<'_>) -> Result<(), std::fmt::Error> {60 -1 return write!(f, "{}", self);61 -1 }62 -1 }63 -164 -1 impl Neg for Rational {65 -1 type Output = Self;66 -167 -1 fn neg(self) -> Self {68 -1 return Self::new(-self.numerator, self.denominator);69 -1 }70 -1 }71 -172 -1 impl Add<Self> for Rational {73 -1 type Output = Self;74 -175 -1 fn add(self, other: Self) -> Self {76 -1 return Self::new(77 -1 (self.numerator * other.denominator).checked_add(other.numerator * self.denominator).unwrap(),78 -1 self.denominator * other.denominator,79 -1 );80 -1 }81 -1 }82 -183 -1 impl Sub<Self> for Rational {84 -1 type Output = Self;85 -186 -1 fn sub(self, other: Self) -> Self {87 -1 return self + -other;88 -1 }89 -1 }90 -191 -1 impl Mul<Self> for Rational {92 -1 type Output = Self;93 -194 -1 fn mul(self, other: Self) -> Self {95 -1 return Self::new(96 -1 self.numerator * other.numerator,97 -1 self.denominator * other.denominator,98 -1 );99 -1 }100 -1 }101 -1102 -1 impl Div<Self> for Rational {103 -1 type Output = Self;104 -1105 -1 fn div(self, other: Self) -> Self {106 -1 let r = Self::new(107 -1 self.numerator * other.denominator,108 -1 self.denominator * other.numerator,109 -1 );110 -1 println!("{} / {} = {}", self, other, r);111 -1 return r;112 -1 }113 -1 }
diff --git a/2023/24/solution.rs b/2023/24/solution.rs
@@ -1,158 +0,0 @@1 -1 #[path = "../lib.rs"]2 -1 mod lib;3 -14 -1 #[path = "./r.rs"]5 -1 mod r;6 -17 -1 use std::convert::TryInto;8 -19 -1 type F = r::Rational;10 -111 -1 fn f(i: i128) -> F {12 -1 return F::n(i);13 -1 }14 -115 -1 fn unf(f: F) -> i128 {16 -1 println!("{}", f);17 -1 assert!(f.numerator % f.denominator == 0);18 -1 return f.numerator / f.denominator;19 -1 }20 -121 -1 fn parse_input() -> Vec<([i128; 3], [i128; 3])> {22 -1 return lib::iter_input().map(|line| {23 -1 let (a, b) = line.split_once('@').unwrap();24 -1 let p: Vec<i128> = a.split(',').map(|s| s.trim().parse().unwrap()).collect();25 -1 let d: Vec<i128> = b.split(',').map(|s| s.trim().parse().unwrap()).collect();26 -1 return (27 -1 p.try_into().unwrap(),28 -1 d.try_into().unwrap(),29 -1 );30 -1 }).collect();31 -1 }32 -133 -1 fn intersect(h1: ([i128; 3], [i128; 3]), h2: ([i128; 3], [i128; 3])) -> bool {34 -1 // 200_000_000_000_000 <= x1 + t1*dx1 = x2 + t2*dx2 <= 400_000_000_000_00035 -1 // 200_000_000_000_000 <= y1 + t1*dy1 = y2 + t2*dy2 <= 400_000_000_000_00036 -1 // t1 = (x2 - x1 + t2*dx2) / dx137 -1 // y1 + (x2 - x1 + t2*dx2) / dx1 * dy1 = y2 + t2*dy238 -1 // y1 + x2*dy1/dx1 - x1*dy1/dx1 + t2*dx2*dy1/dx1 = y2 + t2*dy239 -1 // y1 - y2 + x2*dy1/dx1 - x1*dy1/dx1 = t2*dy2 - t2*dx2*dy1/dx140 -1 // y1 - y2 + x2*dy1/dx1 - x1*dy1/dx1 = t2 * (dy2 - dx2*dy1/dx1)41 -1 // t2 = ((y1 - y2) + (x2 - x1)*dy1/dx1) / (dy2 - dx2*dy1/dx1)42 -1 // t2 = ((y1 - y2)*dx1 - (x1 - x2)*dy1) / (dy2*dx1 - dx2*dy1)43 -144 -1 // in xy, lines intersect if they are not parallel45 -1 // dy1 / dx1 != dy2 / dx246 -1 // dy1 * dx2 != dy2 * dx147 -148 -1 let ([x1, y1, _z1], [dx1, dy1, _dz1]) = h1;49 -1 let ([x2, y2, _z2], [dx2, dy2, _dz2]) = h2;50 -151 -1 let d = dy1 * dx2 - dx1 * dy2;52 -1 if d == 0 {53 -1 return false;54 -1 }55 -156 -1 let dt1 = (y2 - y1) * dx2 - (x2 - x1) * dy2;57 -1 if (dt1 < 0 && d >= 0) || (dt1 >= 0 && d < 0) {58 -1 return false;59 -1 }60 -161 -1 let dt2 = (y2 - y1) * dx1 - (x2 - x1) * dy1;62 -1 if (dt2 < 0 && d >= 0) || (dt2 >= 0 && d < 0) {63 -1 return false;64 -1 }65 -166 -1 let x = unf(f(x1) + f(dx1) * f(dt1) / f(d));67 -1 let y = unf(f(y1) + f(dy1) * f(dt1) / f(d));68 -169 -1 // let min = 7.0;70 -1 // let max = 27.0;71 -1 let min = 200_000_000_000_000;72 -1 let max = 400_000_000_000_000;73 -174 -1 return x >= min && x <= max && y >= min && y <= max;75 -1 }76 -177 -1 fn part1(hail: &Vec<([i128; 3], [i128; 3])>) -> i128 {78 -1 let mut count = 0;79 -1 for i in 0..hail.len() {80 -1 for j in 0..i {81 -1 if intersect(hail[i], hail[j]) {82 -1 count += 1;83 -1 }84 -1 }85 -1 }86 -1 return count;87 -1 }88 -189 -1 fn solve<const N: usize>(matrix: &[[F; N]; N], b: &[F; N]) -> [F; N] {90 -1 let mut tmp = matrix.clone();91 -1 let mut result = b.clone();92 -193 -1 for k in 0..N {94 -1 result[k] = result[k] / tmp[k][k];95 -1 for j in (k..N).rev() {96 -1 tmp[k][j] = tmp[k][j] / tmp[k][k];97 -1 }98 -199 -1 for i in (k + 1)..N {100 -1 result[i] = result[i] - result[k] * tmp[i][k];101 -1 for j in (k..N).rev() {102 -1 tmp[i][j] = tmp[i][j] - tmp[k][j] * tmp[i][k];103 -1 }104 -1 }105 -1 }106 -1107 -1 for k in (0..N).rev() {108 -1 for i in 0..k {109 -1 result[i] = result[i] - result[k] * tmp[i][k];110 -1 }111 -1 }112 -1113 -1 return result;114 -1 }115 -1116 -1117 -1 fn part2(hail: &Vec<([i128; 3], [i128; 3])>) -> i128 {118 -1 // x + ti*dx = xi + ti*dxi119 -1 // y + ti*dy = yi + ti*dyi120 -1 // z + ti*dz = zi + ti*dzi121 -1122 -1 // (p - pi) / (di - d) = ti123 -1 // (x - xi) / (dxi - dx) = ti124 -1125 -1 // (p - pi) / (di - d) = (x - xi) / (dxi - dx)126 -1 // p*dxi - d*xi - x*di + dx*pi + x*d - p*dx = pi*dxi - xi*di127 -1 // p*(dxi - dxj) - d*(xi - xj) - x*(di - dj) + dx*(pi - pj) = pi*dxi - xi*di - pj*dxj + xj*dj128 -1129 -1 let mut matrix = [[f(0); 4]; 4];130 -1 let mut b = [f(0); 4];131 -1132 -1 let ([xj, yj, zj], [dxj, dyj, dzj]) = hail[0];133 -1 let pj = xj + yj + zj;134 -1 let dj = dxj + dyj + dzj;135 -1136 -1 for i in 0..4 {137 -1 let ([xi, yi, zi], [dxi, dyi, dzi]) = hail[i + 1];138 -1 let pi = xi + yi + zi;139 -1 let di = dxi + dyi + dzi;140 -1141 -1 matrix[i][0] = f(dxi - dxj);142 -1 matrix[i][1] = f(xj - xi);143 -1 matrix[i][2] = f(dj - di);144 -1 matrix[i][3] = f(pi - pj);145 -1 b[i] = f(pi * dxi - xi * di - pj * dxj + xj * dj);146 -1 }147 -1148 -1 let result = solve(&matrix, &b);149 -1150 -1 return unf(result[0]);151 -1 }152 -1153 -1 fn main() {154 -1 let hail = parse_input();155 -1156 -1 println!("part1: {}", part1(&hail));157 -1 println!("part2: {}", part2(&hail));158 -1 }