update IQuBit and added getter
This commit is contained in:
parent
d4208308bc
commit
7653379aec
1 changed files with 95 additions and 71 deletions
|
|
@ -5,32 +5,17 @@ from QElephant.Matrix import *
|
|||
|
||||
I = complex(0, 1)
|
||||
|
||||
class QuBit:
|
||||
def __init__(self, alpha: complex=1, beta: complex=0):
|
||||
if abs(alpha)**2 + abs(beta)**2 != 1:
|
||||
raise Exception("The initial state must be normalized")
|
||||
self.__state = [alpha, beta]
|
||||
|
||||
def __str__(self) -> str:
|
||||
return f"{round(self.__state[0], 3)} |0> + {round(self.__state[1], 3)} |1>"
|
||||
|
||||
def __apply(self, matrix: Matrix) -> None:
|
||||
self.__state = matrix._Matrix__apply(self.__state)
|
||||
|
||||
def observe(self) -> list[int]:
|
||||
r = rd.random()
|
||||
if r < abs(self.__state[0])**2:
|
||||
self.__state = [1, 0]
|
||||
return 0
|
||||
self.__state = [0, 1]
|
||||
return 1
|
||||
## Classes
|
||||
|
||||
class MuBit:
|
||||
def __init__(self, n: int) -> None:
|
||||
self.n = n
|
||||
self.__state: list[complex] = [0]*(2**self.n)
|
||||
self.__n = n
|
||||
self.__state: list[complex] = [0]*(2**self.__n)
|
||||
self.__state[0] = 1
|
||||
|
||||
def get_size(self) -> int:
|
||||
return self.__n
|
||||
|
||||
def __str__(self) -> str:
|
||||
def next(N: str) -> str:
|
||||
if N == "":
|
||||
|
|
@ -41,8 +26,8 @@ class MuBit:
|
|||
return (next(N[:-1]))+"0"
|
||||
|
||||
txt = ""
|
||||
N = "0"*self.n
|
||||
for i in range(2**self.n):
|
||||
N = "0"*self.__n
|
||||
for i in range(2**self.__n):
|
||||
txt += f"{round(self.__state[i], 3)} |{N}>\n"
|
||||
N = next(N)
|
||||
return txt
|
||||
|
|
@ -52,7 +37,7 @@ class MuBit:
|
|||
assert(value in {0, 1})
|
||||
|
||||
M = Matrix([[1]])
|
||||
for j in range(self.n):
|
||||
for j in range(self.__n):
|
||||
if j == i:
|
||||
M *= Matrix([[1-value, 0], [0, value]])
|
||||
else:
|
||||
|
|
@ -62,9 +47,9 @@ class MuBit:
|
|||
self.__state = [x/norm for x in self.__state]
|
||||
|
||||
def __iter__(self):
|
||||
return iter([IQuBit(i, self) for i in range(self.n)])
|
||||
return iter([IQuBit(i, self) for i in range(self.__n)])
|
||||
|
||||
def __getitem__(self, item: int) -> "IQuBit":
|
||||
def __getitem__(self, item: int) -> "QuBit":
|
||||
return IQuBit(item, self)
|
||||
|
||||
def __apply(self, i: int, matrix: Matrix) -> None:
|
||||
|
|
@ -81,7 +66,7 @@ class MuBit:
|
|||
def __mapply(self, matrix: Matrix, i: int) -> None:
|
||||
M = Matrix([[1]])
|
||||
j = 0
|
||||
while j < self.n:
|
||||
while j < self.__n:
|
||||
if j == i:
|
||||
M *= matrix
|
||||
j += 2
|
||||
|
|
@ -109,77 +94,122 @@ class MuBit:
|
|||
l.append(IQuBit(i, self).observe())
|
||||
return l
|
||||
|
||||
class IQuBit:
|
||||
def __init__(self, n: int, mb: MuBit) -> None:
|
||||
self.n = n
|
||||
self.__muBit = mb
|
||||
class QuBit:
|
||||
def __init__(self, alpha: complex=1, beta: complex=0):
|
||||
if abs(alpha)**2 + abs(beta)**2 != 1:
|
||||
raise Exception("The initial state must be normalized")
|
||||
self.__state = [alpha, beta]
|
||||
self.__intricated = False
|
||||
|
||||
def is_intricated(self) -> bool:
|
||||
return self.__intricated
|
||||
|
||||
def get_Mubit(self) -> None:
|
||||
return None
|
||||
|
||||
def __str__(self) -> str:
|
||||
return f"{round(self.__state[0], 3)} |0> + {round(self.__state[1], 3)} |1>"
|
||||
|
||||
def __apply(self, matrix: Matrix) -> None:
|
||||
self.__muBit._MuBit__apply(self.n, matrix)
|
||||
self.__state = matrix._Matrix__apply(self.__state)
|
||||
|
||||
def observe(self) -> list[int]:
|
||||
r = rd.random()
|
||||
if r < abs(self.__state[0])**2:
|
||||
self.__state = [1, 0]
|
||||
return 0
|
||||
self.__state = [0, 1]
|
||||
return 1
|
||||
|
||||
class IQuBit(QuBit):
|
||||
def __init__(self, n: int, mb: MuBit) -> None:
|
||||
super().__init__()
|
||||
self.__n = n
|
||||
self.__muBit = mb
|
||||
self.__intricated = True
|
||||
|
||||
def is_intricated(self) -> bool:
|
||||
return self.__intricated
|
||||
|
||||
def get_Mubit(self) -> tuple[MuBit, int]:
|
||||
return (self.__muBit, self.__n)
|
||||
|
||||
def __str__(self) -> str:
|
||||
p = self.__muBit._MuBit__getProb(self.__n)
|
||||
return str(QuBit(math.sqrt(p), math.sqrt(1-p)))
|
||||
|
||||
def __apply(self, matrix: Matrix) -> None:
|
||||
self.__muBit._MuBit__apply(self.__n, matrix)
|
||||
|
||||
def observe(self) -> int:
|
||||
r = rd.random()
|
||||
if r < self.__muBit._MuBit__getProb(self.n):
|
||||
self.__muBit._MuBit__set(self.n, 0)
|
||||
if r < self.__muBit._MuBit__getProb(self.__n):
|
||||
self.__muBit._MuBit__set(self.__n, 0)
|
||||
return 0
|
||||
self.__muBit._MuBit__set(self.n, 1)
|
||||
self.__muBit._MuBit__set(self.__n, 1)
|
||||
return 1
|
||||
|
||||
def H(q: (QuBit | IQuBit)) -> None:
|
||||
if type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.H())
|
||||
elif type(q) == IQuBit:
|
||||
|
||||
|
||||
|
||||
|
||||
## Fonctions
|
||||
|
||||
def H(q: QuBit) -> None:
|
||||
if type(q) == IQuBit:
|
||||
q._IQuBit__apply(Matrix.H())
|
||||
elif type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.H())
|
||||
|
||||
def X(q: (QuBit | IQuBit)) -> None:
|
||||
if type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.X())
|
||||
elif type(q) == IQuBit:
|
||||
def X(q: QuBit) -> None:
|
||||
if type(q) == IQuBit:
|
||||
q._IQuBit__apply(Matrix.X())
|
||||
elif type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.X())
|
||||
|
||||
def Y(q: (QuBit | IQuBit)) -> None:
|
||||
if type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.Y())
|
||||
elif type(q) == IQuBit:
|
||||
def Y(q: QuBit) -> None:
|
||||
if type(q) == IQuBit:
|
||||
q._IQuBit__apply(Matrix.Y())
|
||||
elif type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.Y())
|
||||
|
||||
def Z(q: (QuBit | IQuBit)) -> None:
|
||||
if type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.Z())
|
||||
elif type(q) == IQuBit:
|
||||
def Z(q: QuBit) -> None:
|
||||
if type(q) == IQuBit:
|
||||
q._IQuBit__apply(Matrix.Z())
|
||||
elif type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.Z())
|
||||
|
||||
def S(q: (QuBit | IQuBit)) -> None:
|
||||
if type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.S())
|
||||
elif type(q) == IQuBit:
|
||||
def S(q: QuBit) -> None:
|
||||
if type(q) == IQuBit:
|
||||
q._IQuBit__apply(Matrix.S())
|
||||
elif type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.S())
|
||||
|
||||
def T(q: (QuBit | IQuBit)) -> None:
|
||||
if type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.T())
|
||||
elif type(q) == IQuBit:
|
||||
def T(q: QuBit) -> None:
|
||||
if type(q) == IQuBit:
|
||||
q._IQuBit__apply(Matrix.T())
|
||||
elif type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.T())
|
||||
|
||||
def Rx(q: (QuBit | IQuBit), phi: float) -> None:
|
||||
def Rx(q: QuBit, phi: float) -> None:
|
||||
if type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.Rx(phi))
|
||||
elif type(q) == IQuBit:
|
||||
q._IQuBit__apply(Matrix.Rx(phi))
|
||||
|
||||
def Ry(q: (QuBit | IQuBit), phi: float) -> None:
|
||||
def Ry(q: QuBit, phi: float) -> None:
|
||||
if type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.Ry(phi))
|
||||
elif type(q) == IQuBit:
|
||||
q._IQuBit__apply(Matrix.Ry(phi))
|
||||
|
||||
def Rz(q: (QuBit | IQuBit), phi: float) -> None:
|
||||
def Rz(q: QuBit, phi: float) -> None:
|
||||
if type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.Rz(phi))
|
||||
elif type(q) == IQuBit:
|
||||
q._IQuBit__apply(Matrix.Rz(phi))
|
||||
|
||||
def R1(q: (QuBit | IQuBit), phi: float) -> None:
|
||||
def R1(q: QuBit, phi: float) -> None:
|
||||
if type(q) == QuBit:
|
||||
q._QuBit__apply(Matrix.R1(phi))
|
||||
elif type(q) == IQuBit:
|
||||
|
|
@ -217,10 +247,4 @@ def test(q: QuBit) -> None:
|
|||
|
||||
if __name__=="__main__":
|
||||
q = MuBit(3)
|
||||
H(q[0])
|
||||
# H(q[1])
|
||||
print(q)
|
||||
|
||||
CNOT(q, 0, 1)
|
||||
|
||||
print(q)
|
||||
s = q[1].get_Mubit()
|
||||
Loading…
Reference in a new issue