def openql_program_from_pygsti_expList(pygsti_gateset, program_name: str, qubits: list, platf_cfg: str, start_idx:int=0, recompile=True): platf = Platform('OpenQL_Platform', platf_cfg) p = Program(pname=program_name, nqubits=platf.get_qubit_number(), p=platf) p.output_dir = ql.get_output_dir() p.filename = join(p.output_dir, p.name + '.qisa') if oqh.check_recompilation_needed(p.filename, platf_cfg, recompile): for i, gatestring in enumerate(pygsti_gateset): kernel_name = 'G {} {}'.format(i, gatestring) k = openql_kernel_from_gatestring( gatestring=gatestring, qubits=qubits, kernel_name=kernel_name, platf=platf) p.add_kernel(k) with suppress_stdout(): p.compile() p.sweep_points = np.arange(len(pygsti_gateset), dtype=float)+ start_idx p.set_sweep_points(p.sweep_points, len(p.sweep_points)) return p
def ef_rabi_seq(q0: int, amps: list, platf_cfg: str, recovery_pulse: bool = True, add_cal_points: bool = True): """ Sequence used to calibrate pulses for 2nd excited state (ef/12 transition) Timing of the sequence: q0: -- X180 -- X12 -- (X180) -- RO Args: q0 (str): name of the addressed qubit amps (list): amps for the two state pulse, note that these are only used to label the kernels. Load the pulse in the LutMan recovery_pulse (bool): if True adds a recovery pulse to enhance contrast in the measured signal. """ if len(amps) > 18: raise ValueError('Only 18 free codewords available for amp pulses') platf = Platform('OpenQL_Platform', platf_cfg) p = Program(pname="ef_rabi_seq", nqubits=platf.get_qubit_number(), p=platf) # These angles correspond to special pi/2 pulses in the lutman for i, amp in enumerate(amps): # cw_idx corresponds to special hardcoded pulses in the lutman cw_idx = i + 9 k = Kernel("ef_A{}".format(amp), p=platf) k.prepz(q0) k.gate('rx180', q0) k.gate('cw_{:02}'.format(cw_idx), q0) if recovery_pulse: k.gate('rx180', q0) k.measure(q0) p.add_kernel(k) if add_cal_points: p = add_single_qubit_cal_points(p, platf=platf, qubit_idx=q0) with suppress_stdout(): p.compile() # attribute get's added to program to help finding the output files p.output_dir = ql.get_output_dir() p.filename = join(p.output_dir, p.name + '.qisa') if add_single_qubit_cal_points: cal_pts_idx = [ amps[-1] + .1, amps[-1] + .15, amps[-1] + .2, amps[-1] + .25 ] else: cal_pts_idx = [] p.sweep_points = np.concatenate([amps, cal_pts_idx]) p.set_sweep_points(p.sweep_points, len(p.sweep_points)) return p
def AllXY(qubit_idx: int, platf_cfg: str, double_points: bool = True): """ Single qubit AllXY sequence. Writes output files to the directory specified in openql. Output directory is set as an attribute to the program for convenience. Input pars: qubit_idx: int specifying the target qubit (starting at 0) platf_cfg: filename of the platform config file double_points: if true repeats every element twice Returns: p: OpenQL Program object containing """ platf = Platform('OpenQL_Platform', platf_cfg) p = Program(pname="AllXY", nqubits=platf.get_qubit_number(), p=platf) allXY = [['i', 'i'], ['rx180', 'rx180'], ['ry180', 'ry180'], ['rx180', 'ry180'], ['ry180', 'rx180'], ['rx90', 'i'], ['ry90', 'i'], ['rx90', 'ry90'], ['ry90', 'rx90'], ['rx90', 'ry180'], ['ry90', 'rx180'], ['rx180', 'ry90'], ['ry180', 'rx90'], ['rx90', 'rx180'], ['rx180', 'rx90'], ['ry90', 'ry180'], ['ry180', 'ry90'], ['rx180', 'i'], ['ry180', 'i'], ['rx90', 'rx90'], ['ry90', 'ry90']] # this should be implicit p.set_sweep_points(np.arange(len(allXY), dtype=float), len(allXY)) for i, xy in enumerate(allXY): if double_points: js = 2 else: js = 1 for j in range(js): k = Kernel("AllXY_" + str(i + j / 2), p=platf) k.prepz(qubit_idx) k.gate(xy[0], qubit_idx) k.gate(xy[1], qubit_idx) k.measure(qubit_idx) p.add_kernel(k) with suppress_stdout(): p.compile(verbose=False) # attribute get's added to program to help finding the output files p.output_dir = ql.get_output_dir() p.filename = join(p.output_dir, p.name + '.qisa') return p
def idle_error_rate_seq(nr_of_idle_gates, states: list, gate_duration_ns: int, echo: bool, qubit_idx: int, platf_cfg: str, post_select=True): """ Sequence to perform the idle_error_rate_sequence. Virtually identical to a T1 experiment (Z-basis) or a ramsey/echo experiment (X-basis) Input pars: nr_of_idle_gates : list of integers specifying the number of idle gates corresponding to each data point. gate_duration_ns : integer specifying the duration of the wait gate. states : list of states to prepare qubit_idx: int specifying the target qubit (starting at 0) platf_cfg: filename of the platform config file Returns: p: OpenQL Program object containing """ allowed_states = ['0', '1', '+'] platf = Platform('OpenQL_Platform', platf_cfg) p = Program(pname="idle_error_rate", nqubits=platf.get_qubit_number(), p=platf) sweep_points = [] for N in nr_of_idle_gates: for state in states: if state not in allowed_states: raise ValueError('State must be in {}'.format(allowed_states)) k = Kernel("idle_prep{}_N{}".format(state, N), p=platf) # 1. Preparing in the right basis k.prepz(qubit_idx) if post_select: # adds an initialization measurement used to post-select k.measure(qubit_idx) if state == '1': k.gate('rx180', qubit_idx) elif state == '+': k.gate('rym90', qubit_idx) # 2. The "waiting" gates wait_nanoseconds = N * gate_duration_ns if state == '+' and echo: k.gate("wait", [qubit_idx], wait_nanoseconds // 2) k.gate('rx180', qubit_idx) k.gate("wait", [qubit_idx], wait_nanoseconds // 2) else: k.gate("wait", [qubit_idx], wait_nanoseconds) # 3. Reading out in the proper basis if state == '+' and echo: k.gate('rym90', qubit_idx) elif state == '+': k.gate('ry90', qubit_idx) k.measure(qubit_idx) p.add_kernel(k) sweep_points.append(N) p.set_sweep_points(sweep_points, num_sweep_points=len(sweep_points)) p.sweep_points = sweep_points with suppress_stdout(): p.compile(verbose=False) # attribute get's added to program to help finding the output files p.output_dir = ql.get_output_dir() p.filename = join(p.output_dir, p.name + '.qisa') return p