86 lines
2.0 KiB
Python
86 lines
2.0 KiB
Python
from .week1 import blood_cell_compatibility_lookup, BloodType
|
|
import random
|
|
|
|
|
|
class Dealer:
|
|
def __init__(self):
|
|
T = [[blood_cell_compatibility_lookup(r, d)
|
|
for d in BloodType ]
|
|
for r in BloodType]
|
|
self.M_B = [[random.randint(0, 1) for _ in range(8)] for _ in range(8)]
|
|
|
|
self.r = random.randint(0, 8)
|
|
self.s = random.randint(0, 8)
|
|
|
|
self.M_A = [[self.M_B[i][j] ^ T[i - self.r][j - self.s] for j in range(8)] for i in range(8)]
|
|
|
|
def rand_a(self):
|
|
return self.r, self.M_A
|
|
|
|
def rand_b(self):
|
|
return self.s, self.M_B
|
|
|
|
|
|
class Alice:
|
|
def __init__(self, x, r, M_A):
|
|
self.x = x
|
|
self.r = r
|
|
self.M_A = M_A
|
|
|
|
def send(self):
|
|
# Should return u = x+r mod 2^n
|
|
self.u = (self.x + self.r) % 8
|
|
return self.u
|
|
|
|
def receive(self, v, z_b):
|
|
self.v = v
|
|
self.z_b = z_b
|
|
|
|
def output(self):
|
|
z = self.M_A[self.u][self.v] ^ self.z_b
|
|
return z
|
|
|
|
|
|
class Bob:
|
|
def __init__(self, y, s, M_B):
|
|
self.y = y
|
|
self.s = s
|
|
self.M_B = M_B
|
|
|
|
def send(self):
|
|
# Should return v = y+s mod 2^n
|
|
v = (self.y + self.s) % 8
|
|
z_b = self.M_B[self.u][v]
|
|
|
|
return v, z_b
|
|
|
|
def receive(self, u):
|
|
self.u = u
|
|
|
|
|
|
def ottt(recipient, donor):
|
|
dealer = Dealer()
|
|
alice = Alice(recipient, *dealer.rand_a())
|
|
bob = Bob(donor, *dealer.rand_b())
|
|
bob.receive(alice.send())
|
|
alice.receive(*bob.send())
|
|
z = alice.output()
|
|
return z
|
|
|
|
|
|
def main():
|
|
green = 0
|
|
red = 0
|
|
for i, recipient in enumerate(BloodType):
|
|
for j, donor in enumerate(BloodType):
|
|
z = ottt(i, j)
|
|
lookup = blood_cell_compatibility_lookup(recipient, donor)
|
|
if lookup == z:
|
|
green += 1
|
|
else:
|
|
print(f"'{BloodType(donor).name} -> {BloodType(recipient).name}' should be {lookup}.")
|
|
red += 1
|
|
print("Green:", green)
|
|
print("Red :", red)
|
|
|