finish level3/doomsday-fuel

This commit is contained in:
Seongbeom Park 2022-01-11 23:45:23 +09:00
parent fbeaef40c5
commit e16232c3a3
2 changed files with 102 additions and 0 deletions

View File

@ -1,2 +1,7 @@
# Google Foobar Challenge # Google Foobar Challenge
## Level3
### doomsday-fuel
* Reference
* L26.6 Absorption Probabilities, MIT OpenCourseWare, https://www.youtube.com/watch?v=vEsUsaK1HBk

View File

@ -0,0 +1,97 @@
import numpy as np
def solution(m):
stable_ores, unstable_ores = categorize_ores(m)
if 0 in stable_ores:
return [1]+[0]*(len(stable_ores)-1)+[1]
p = np.array(m)
q = np.zeros(p.shape, dtype=int)
for i in range(len(m)):
q[i][i] = sum(p[i])
r = q - p
t = gaussian_elimination(r, stable_ores, unstable_ores)
numerators = -t[0][stable_ores]
denominator = sum(numerators)
result = np.hstack((numerators, denominator))
g = abs_gcd(*list(result))
return list(result / g)
def categorize_ores(m):
stable_ores = []
unstable_ores = []
for i in range(len(m)):
if sum(m[i]) == 0:
stable_ores += [i]
else:
unstable_ores += [i]
return stable_ores, unstable_ores
def gaussian_elimination(r, s, u):
arr = r
for i in range(len(u)):
for j in range(i+1, len(u)):
row_up, row_down = arr[u[i]], arr[u[j]]
if row_down[u[i]] != 0:
arr[u[j]] = row_down*arr[u[i]][u[i]] - row_up*arr[u[j]][u[i]]
arr[u[j]] = arr[u[j]] / abs_gcd(*list(arr[u[j]]))
for i in reversed(range(len(u))):
for j in reversed(range(i)):
row_down, row_up = arr[u[i]], arr[u[j]]
if row_up[u[i]] != 0:
arr[u[j]] = row_up*row_down[u[i]] - row_down*row_up[u[i]]
arr[u[j]] = arr[u[j]] / abs_gcd(*list(arr[u[j]]))
return arr
def abs_gcd(*args):
if len(args) == 1:
return abs(args[0])
if len(args) == 2:
m, n = abs(args[0]), abs(args[1])
while n != 0:
t = m % n
m, n = n, t
return abs(m)
return abs_gcd(args[0], abs_gcd(*args[1:]))
tests = [
[
[[0, 2, 1, 0, 0], [0, 0, 0, 3, 4], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0]],
[7, 6, 8, 21]
],
[
[[0, 1, 0, 0, 0, 1], [4, 0, 0, 3, 2, 0], [0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0]],
[0, 3, 2, 9, 14]
],
[
[[0, 1, 0, 0, 0, 1], [4, 0, 0, 3, 2, 0], [0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 1], [0, 0, 0, 0, 0, 0]],
[0, 3, 11, 14]
],
[
[[0, 1, 0, 0, 0, 1], [4, 0, 0, 3, 2, 0], [0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 1], [0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0]],
[0, 1, 6, 7]
],
[
[[0]],
[1, 1]
],
[
[[0, 1], [0, 0]],
[1, 1]
],
[
[[0, 5, 0, 3], [0, 0, 4, 1], [0, 0, 0, 0], [0, 0, 0, 0]],
[1, 1, 2]
],
]
#print(solution(tests[1][0]), tests[1][1])
for test in tests:
result = solution(test[0])
print(result == test[1], result, test[1])