Safe Haskell | None |
---|
This library provides various transformers and functions for performing dynamic liftings based on different mechanisms. Some use simulations to do the dynamic liftings; others just do them randomly. There are also functions for printing the simulated circuit.
This code is experimental.
Synopsis
- type RandomCirc a = StateT StdGen Circ a
- type ListCirc a = StateT [Bool] Circ a
- evalRandomCirc :: Int -> RandomCirc a -> Circ a
- evalListCirc :: [Bool] -> ListCirc a -> Circ a
- evalRandomCirc_unary :: Int -> (a -> RandomCirc b) -> a -> Circ b
- evalListCirc_unary :: [Bool] -> (a -> ListCirc b) -> a -> Circ b
- randomRRandomCirc :: Random a => (a, a) -> RandomCirc a
- print_unary_random :: QCData qa => Format -> (qa -> RandomCirc b) -> qa -> IO ()
- print_unary_list :: QCData qa => Format -> Int -> (qa -> ListCirc b) -> qa -> IO ()
- lifted_identity_transformer :: MonadTrans t => Transformer (t Circ) Qubit Bit
- random_dynamic_lift :: Bit -> RandomCirc Bool
- list_dynamic_lift :: Bit -> ListCirc Bool
- random_dynamic_lift_transformer :: DynamicTransformer (StateT StdGen Circ) Qubit Bit
- list_dynamic_lift_transformer :: DynamicTransformer (StateT [Bool] Circ) Qubit Bit
- print_unary_with_random_liftings :: (QCData a, QCData b) => Format -> (a -> Circ b) -> a -> IO ()
- print_unary_with_list_liftings :: (QCData a, QCData b) => Format -> Int -> (a -> Circ b) -> a -> IO ()
- data SimulationState = SS {}
- empty_simulation_state :: Int -> SimulationState
- type SimulatedCirc a = StateT SimulationState Circ a
- evalSimulatedCirc :: Int -> SimulatedCirc a -> Circ a
- evalSimulatedCirc_unary :: Int -> (a -> SimulatedCirc b) -> a -> Circ b
- randomRSimulatedCirc :: Random a => (a, a) -> SimulatedCirc a
- putQS :: Amplitudes Double -> SimulatedCirc ()
- putCS :: Map Bit Bool -> SimulatedCirc ()
- s_classical_control :: Map Bit Bool -> Signed (B_Endpoint Qubit Bit) -> Bool
- s_classical_controls :: Map Bit Bool -> Ctrls Qubit Bit -> Bool
- s_qc_control :: Map Bit Bool -> Map Qubit Bool -> Signed (B_Endpoint Qubit Bit) -> Bool
- s_qc_controls :: Map Bit Bool -> Map Qubit Bool -> Ctrls Qubit Bit -> Bool
- s_if_controls :: Map Bit Bool -> Ctrls Qubit Bit -> (Map Qubit Bool -> Amplitudes Double) -> Map Qubit Bool -> Amplitudes Double
- simulated_lift_transformer :: Transformer (StateT SimulationState Circ) Qubit Bit
- simulated_dynamic_lift :: Bit -> SimulatedCirc Bool
- simulated_dynamic_lift_transformer :: DynamicTransformer (StateT SimulationState Circ) Qubit Bit
- print_simulated :: Format -> SimulatedCirc b -> IO ()
- print_unary_with_simulated_liftings :: (QCData a, QCData b) => Format -> (a -> Circ b) -> BType a -> IO ()
- simulate_liftings_unary :: (QCData a, QCData b) => Int -> (a -> Circ b) -> BType a -> Circ b
Random Dynamic Liftings and Liftings from a List
evalRandomCirc :: Int -> RandomCirc a -> Circ a Source #
To evaluate a RandomCirc
we require a seed for the random generator.
evalListCirc :: [Bool] -> ListCirc a -> Circ a Source #
To evaluate a ListCirc
we require a list of booleans.
evalRandomCirc_unary :: Int -> (a -> RandomCirc b) -> a -> Circ b Source #
Lift evalRandomCirc
to unary random circuit generating functions.
evalListCirc_unary :: [Bool] -> (a -> ListCirc b) -> a -> Circ b Source #
Left evalListCirc
to unary list circuit generating functions.
randomRRandomCirc :: Random a => (a, a) -> RandomCirc a Source #
Lift the underlying randomR
function into the RandomCirc monad.
print_unary_random :: QCData qa => Format -> (qa -> RandomCirc b) -> qa -> IO () Source #
Print a RandomCirc by evaluating it with a seed in the IO monad.
print_unary_list :: QCData qa => Format -> Int -> (qa -> ListCirc b) -> qa -> IO () Source #
Print a LiftCirc by evaluating it in the IO Monad, so as to read in a given number of booleans.
lifted_identity_transformer :: MonadTrans t => Transformer (t Circ) Qubit Bit Source #
Lift the identity_transformer
using any monad transformer.
random_dynamic_lift :: Bit -> RandomCirc Bool Source #
Dynamic lifting can make use of a random result (without caring which wire is being lifted).
list_dynamic_lift :: Bit -> ListCirc Bool Source #
Dynamic lifting can pop the head off of a list of booleans, and use that to lift the given wire.
random_dynamic_lift_transformer :: DynamicTransformer (StateT StdGen Circ) Qubit Bit Source #
A dynamic transformer which is the identity transformer (lifted to RandomCirc), except for the dynamic lifting operation.
list_dynamic_lift_transformer :: DynamicTransformer (StateT [Bool] Circ) Qubit Bit Source #
A dynamic transformer which is the identity transformer (lifted to ListCirc), except for the dynamic lifting operation.
print_unary_with_random_liftings :: (QCData a, QCData b) => Format -> (a -> Circ b) -> a -> IO () Source #
Print a circuit, using random dynamic liftings.
print_unary_with_list_liftings :: (QCData a, QCData b) => Format -> Int -> (a -> Circ b) -> a -> IO () Source #
Print a circuit, using a list of dynamic liftings.
Simulating the Dynamic Liftings
data SimulationState Source #
Add state to the Circ Monad so that we can simulate the circuit and use that data for dynamic liftings.
empty_simulation_state :: Int -> SimulationState Source #
When we start a simulation, we need an empty starting state, with a seed for the generator.
type SimulatedCirc a = StateT SimulationState Circ a Source #
A State monad that holds our SimulationState.
evalSimulatedCirc :: Int -> SimulatedCirc a -> Circ a Source #
Evaluate a SimulatedCirc
. This requires a seed for the random generator.
evalSimulatedCirc_unary :: Int -> (a -> SimulatedCirc b) -> a -> Circ b Source #
Lift evalSimulatedCirc
to unary functions.
randomRSimulatedCirc :: Random a => (a, a) -> SimulatedCirc a Source #
Lift the underlying randomR
function into the SimulatedCirc monad.
putQS :: Amplitudes Double -> SimulatedCirc () Source #
A specialized put function for the quantum state that uses the current state instead of a previously retrieved state.
putCS :: Map Bit Bool -> SimulatedCirc () Source #
A specialized put function for the classical state that uses the current state instead of a previously retrieved state.
s_classical_control :: Map Bit Bool -> Signed (B_Endpoint Qubit Bit) -> Bool Source #
It doesn't make sense having a quantum control on a classical gate, so we can throw an error if that is the case, and just lookup the boolean result otherwise.
s_classical_controls :: Map Bit Bool -> Ctrls Qubit Bit -> Bool Source #
Map the s_classical_control
function to all the controls, and take the
and
of the result.
s_qc_control :: Map Bit Bool -> Map Qubit Bool -> Signed (B_Endpoint Qubit Bit) -> Bool Source #
When we want a quantum control, we will be working with one "basis state" at a time, and can look up the qubit's value in that basis state to see whether the control fires.
s_qc_controls :: Map Bit Bool -> Map Qubit Bool -> Ctrls Qubit Bit -> Bool Source #
Map the s_qc_control
function to all the controls (under the given basis
state), and take the and
of the result.
s_if_controls :: Map Bit Bool -> Ctrls Qubit Bit -> (Map Qubit Bool -> Amplitudes Double) -> Map Qubit Bool -> Amplitudes Double Source #
Apply the given function only if the controls fire.
simulated_lift_transformer :: Transformer (StateT SimulationState Circ) Qubit Bit Source #
The simulated_lift_transformer
is the actual transformer that does the
simulation, while recreating the circuit.
simulated_dynamic_lift :: Bit -> SimulatedCirc Bool Source #
Dynamic lifting can make use of a simulated result.
simulated_dynamic_lift_transformer :: DynamicTransformer (StateT SimulationState Circ) Qubit Bit Source #
A dynamic transformer which simulates the circuit, whilst reconstructing it with simulated lifting results. Note: do not handle classical controlling.
print_simulated :: Format -> SimulatedCirc b -> IO () Source #
Print a RandomCirc by evaluating it with a seed in the IO monad.
print_unary_with_simulated_liftings :: (QCData a, QCData b) => Format -> (a -> Circ b) -> BType a -> IO () Source #
Print a circuit, using simulated liftings.
simulate_liftings_unary :: (QCData a, QCData b) => Int -> (a -> Circ b) -> BType a -> Circ b Source #
Pass a (possibly) dynamic circuit through the
simulated_dynamic_lift_transformer
and evaluate the liftings so as to
leave us with a static circuit that represents a single run of the original
circuit, with the given inputs. We also need to pass in a seed for the RNG.