def test_from_dict_per_class(self): """Test converting to Qobj and its subclass representations given a dictionary.""" test_parameters = { PulseQobj: (self.valid_qobj, self.valid_dict), PulseQobjConfig: ( PulseQobjConfig(meas_level=1, memory_slot_size=8192, meas_return='avg', pulse_library=[ PulseLibraryItem(name='pulse0', samples=[0.1 + 0.0j]) ], qubit_lo_freq=[4.9], meas_lo_freq=[6.9], rep_time=1000), { 'meas_level': 1, 'memory_slot_size': 8192, 'meas_return': 'avg', 'pulse_library': [{ 'name': 'pulse0', 'samples': [0.1 + 0j] }], 'qubit_lo_freq': [4.9], 'meas_lo_freq': [6.9], 'rep_time': 1000 }, ), PulseLibraryItem: (PulseLibraryItem(name='pulse0', samples=[0.1 + 0.0j]), { 'name': 'pulse0', 'samples': [0.1 + 0j] }), PulseQobjExperiment: (PulseQobjExperiment(instructions=[ PulseQobjInstruction(name='pulse0', t0=0, ch='d0') ]), { 'instructions': [{ 'name': 'pulse0', 't0': 0, 'ch': 'd0' }] }), PulseQobjInstruction: (PulseQobjInstruction(name='pulse0', t0=0, ch='d0'), { 'name': 'pulse0', 't0': 0, 'ch': 'd0' }) } for qobj_class, (qobj_item, expected_dict) in test_parameters.items(): with self.subTest(msg=str(qobj_class)): self.assertEqual(qobj_item, qobj_class.from_dict(expected_dict))
def from_dict(cls, data): """Create a new PulseDefaults object from a dictionary. Args: data (dict): A dictionary representing the PulseDefaults to create. It will be in the same format as output by :meth:`to_dict`. Returns: PulseDefaults: The PulseDefaults from the input dictionary. """ in_data = copy.copy(data) in_data['pulse_library'] = [ PulseLibraryItem.from_dict(x) for x in in_data.pop('pulse_library') ] in_data['cmd_def'] = [ Command.from_dict(x) for x in in_data.pop('cmd_def') ] if 'meas_kernel' in in_data: in_data['meas_kernel'] = MeasurementKernel.from_dict( in_data.pop('meas_kernel')) if 'discriminator' in in_data: in_data['discriminator'] = Discriminator.from_dict( in_data.pop('discriminator')) return cls(**in_data)
def setUp(self): self.linear = SamplePulse(np.arange(0, 0.01), name='linear') self.pulse_library = [PulseLibraryItem(name=self.linear.name, samples=self.linear.samples.tolist())] self.converter = QobjToInstructionConverter(self.pulse_library, buffer=0) self.num_qubits = 2
def setUp(self): self.linear = SamplePulse(np.arange(0, 0.01), name='linear') self.pulse_library = [PulseLibraryItem(name=self.linear.name, samples=self.linear.samples.tolist())] self.converter = QobjToInstructionConverter(self.pulse_library, buffer=0) self.device = PulseChannelSpec(n_qubits=2, n_control=0, n_registers=2)
def assemble_circuits(circuits: List[QuantumCircuit], run_config: RunConfig, qobj_id: int, qobj_header: QobjHeader) -> QasmQobj: """Assembles a list of circuits into a qobj that can be run on the backend. Args: circuits: circuit(s) to assemble run_config: configuration of the runtime environment qobj_id: identifier for the generated qobj qobj_header: header to pass to the results Returns: The qobj to be run on the backends """ qobj_config = QasmQobjConfig() if run_config: qobj_config = QasmQobjConfig(**run_config.to_dict()) qubit_sizes = [] memory_slot_sizes = [] for circ in circuits: num_qubits = 0 memory_slots = 0 for qreg in circ.qregs: num_qubits += qreg.size for creg in circ.cregs: memory_slots += creg.size qubit_sizes.append(num_qubits) memory_slot_sizes.append(memory_slots) qobj_config.memory_slots = max(memory_slot_sizes) qobj_config.n_qubits = max(qubit_sizes) experiments_and_pulse_libs = parallel_map(_assemble_circuit, circuits, [run_config]) experiments = [] pulse_library = {} for exp, lib in experiments_and_pulse_libs: experiments.append(exp) if lib: pulse_library.update(lib) if pulse_library: qobj_config.pulse_library = [ PulseLibraryItem(name=name, samples=samples) for name, samples in pulse_library.items() ] experiments, calibrations = _extract_common_calibrations(experiments) if calibrations and calibrations.gates: qobj_config.calibrations = calibrations return QasmQobj(qobj_id=qobj_id, config=qobj_config, experiments=experiments, header=qobj_header)
def setUp(self): self.linear = SamplePulse(np.arange(0, 0.01), name='linear') self.pulse_library = [ PulseLibraryItem(name=self.linear.name, samples=self.linear.samples.tolist()) ] self.converter = QobjToInstructionConverter(self.pulse_library, buffer=0) self.device = DeviceSpecification(qubits=[ Qubit(0, DriveChannel(0), MeasureChannel(0), AcquireChannel(0)) ], registers=[RegisterSlot(0)], mem_slots=[MemorySlot(0)])
def test_pulse_obj_config_warns(self): """Test that PulseQobjConfig constructor displays a deprecation warning if max_credits is used""" with self.assertWarns(DeprecationWarning): PulseQobjConfig( shots=1024, memory_slots=2, max_credits=10, meas_level=1, memory_slot_size=8192, meas_return="avg", pulse_library=[ PulseLibraryItem( name="pulse0", samples=[0.0 + 0.0j, 0.5 + 0.0j, 0.0 + 0.0j]) ], qubit_lo_freq=[4.9], meas_lo_freq=[6.9], rep_time=1000, )
def __init__(self): configuration = PulseBackendConfiguration( backend_name='fake_openpulse_2q', backend_version='0.0.0', n_qubits=2, meas_levels=[0, 1, 2], basis_gates=['u1', 'u2', 'u3', 'cx', 'id'], simulator=False, local=True, conditional=True, open_pulse=True, memory=False, max_shots=65536, gates=[GateConfig(name='TODO', parameters=[], qasm_def='TODO')], coupling_map=[[1, 0]], n_registers=2, n_uchannels=2, u_channel_lo=[ [UchannelLO(q=0, scale=1. + 0.j)], [UchannelLO(q=0, scale=-1. + 0.j), UchannelLO(q=1, scale=1. + 0.j)] ], meas_level=[1, 2], qubit_lo_range=[[4.5, 5.5], [4.5, 5.5]], meas_lo_range=[[6.0, 7.0], [6.0, 7.0]], dt=1.3333, dtm=10.5, rep_times=[100, 250, 500, 1000], meas_map=[[0, 1]], channel_bandwidth=[ [-0.2, 0.4], [-0.3, 0.3], [-0.3, 0.3], [-0.02, 0.02], [-0.02, 0.02], [-0.02, 0.02] ], meas_kernels=['kernel1'], discriminators=['max_1Q_fidelity'], acquisition_latency=[[100, 100], [100, 100]], conditional_latency=[ [100, 1000], [1000, 100], [100, 1000], [1000, 100], [100, 1000], [1000, 100] ] ) self._defaults = PulseDefaults( qubit_freq_est=[4.9, 5.0], meas_freq_est=[6.5, 6.6], buffer=10, pulse_library=[PulseLibraryItem(name='test_pulse_1', samples=[0.j, 0.1j]), PulseLibraryItem(name='test_pulse_2', samples=[0.j, 0.1j, 1j]), PulseLibraryItem(name='test_pulse_3', samples=[0.j, 0.1j, 1j, 0.5 + 0j])], cmd_def=[Command(name='u1', qubits=[0], sequence=[PulseQobjInstruction(name='fc', ch='d0', t0=0, phase='-P1*np.pi')]), Command(name='u3', qubits=[0], sequence=[PulseQobjInstruction(name='test_pulse_1', ch='d0', t0=0)]), Command(name='u3', qubits=[1], sequence=[PulseQobjInstruction(name='test_pulse_3', ch='d1', t0=0)]), Command(name='cx', qubits=[0, 1], sequence=[PulseQobjInstruction(name='test_pulse_1', ch='d0', t0=0), PulseQobjInstruction(name='test_pulse_2', ch='u0', t0=10), PulseQobjInstruction(name='pv', ch='d1', t0=2, val='cos(P2)'), PulseQobjInstruction(name='test_pulse_1', ch='d1', t0=20), PulseQobjInstruction(name='fc', ch='d1', t0=20, phase=2.1)]), Command(name='measure', qubits=[0], sequence=[PulseQobjInstruction(name='test_pulse_1', ch='m0', t0=0), PulseQobjInstruction(name='acquire', duration=10, t0=0, qubits=[0], memory_slot=[0])])] ) super().__init__(configuration)
def setUp(self): self.valid_qobj = PulseQobj( qobj_id='12345', header=QobjHeader(), config=PulseQobjConfig(shots=1024, memory_slots=2, max_credits=10, meas_level=1, memory_slot_size=8192, meas_return='avg', pulse_library=[ PulseLibraryItem(name='pulse0', samples=[ 0.0 + 0.0j, 0.5 + 0.0j, 0.0 + 0.0j ]) ], qubit_lo_freq=[4.9], meas_lo_freq=[6.9], rep_time=1000), experiments=[ PulseQobjExperiment(instructions=[ PulseQobjInstruction(name='pulse0', t0=0, ch='d0'), PulseQobjInstruction(name='fc', t0=5, ch='d0', phase=1.57), PulseQobjInstruction(name='fc', t0=5, ch='d0', phase=0.), PulseQobjInstruction(name='fc', t0=5, ch='d0', phase='P1'), PulseQobjInstruction( name='pv', t0=10, ch='d0', val=0.1 + 0.0j), PulseQobjInstruction(name='pv', t0=10, ch='d0', val='P1'), PulseQobjInstruction(name='acquire', t0=15, duration=5, qubits=[0], memory_slot=[0], kernels=[ QobjMeasurementOption( name='boxcar', params={ "start_window": 0, "stop_window": 5 }) ]) ]) ]) self.valid_dict = { 'qobj_id': '12345', 'type': 'PULSE', 'schema_version': '1.1.0', 'header': {}, 'config': { 'max_credits': 10, 'memory_slots': 2, 'shots': 1024, 'meas_level': 1, 'memory_slot_size': 8192, 'meas_return': 'avg', 'pulse_library': [{ 'name': 'pulse0', 'samples': [0, 0.5, 0] }], 'qubit_lo_freq': [4.9], 'meas_lo_freq': [6.9], 'rep_time': 1000 }, 'experiments': [{ 'instructions': [{ 'name': 'pulse0', 't0': 0, 'ch': 'd0' }, { 'name': 'fc', 't0': 5, 'ch': 'd0', 'phase': 1.57 }, { 'name': 'fc', 't0': 5, 'ch': 'd0', 'phase': 0 }, { 'name': 'fc', 't0': 5, 'ch': 'd0', 'phase': 'P1' }, { 'name': 'pv', 't0': 10, 'ch': 'd0', 'val': 0.1 + 0j }, { 'name': 'pv', 't0': 10, 'ch': 'd0', 'val': 'P1' }, { 'name': 'acquire', 't0': 15, 'duration': 5, 'qubits': [0], 'memory_slot': [0], 'kernels': [{ 'name': 'boxcar', 'params': { 'start_window': 0, 'stop_window': 5 } }] }] }] }
def assemble_circuits(circuits: List[QuantumCircuit], run_config: RunConfig, qobj_id: int, qobj_header: QobjHeader) -> QasmQobj: """Assembles a list of circuits into a qobj that can be run on the backend. Args: circuits: circuit(s) to assemble run_config: configuration of the runtime environment qobj_id: identifier for the generated qobj qobj_header: header to pass to the results Returns: The qobj to be run on the backends """ # assemble the circuit experiments experiments_and_pulse_libs = parallel_map(_assemble_circuit, circuits, [run_config]) experiments = [] pulse_library = {} for exp, lib in experiments_and_pulse_libs: experiments.append(exp) if lib: pulse_library.update(lib) # extract common calibrations experiments, calibrations = _extract_common_calibrations(experiments) # configure LO freqs per circuit lo_converter = converters.LoConfigConverter(QasmQobjExperimentConfig, **run_config.to_dict()) experiments = _configure_experiment_los(experiments, lo_converter, run_config) qobj_config = QasmQobjConfig() if run_config: qobj_config_dict = run_config.to_dict() # remove LO ranges, not needed in qobj qobj_config_dict.pop("qubit_lo_range", None) qobj_config_dict.pop("meas_lo_range", None) # convert LO frequencies to GHz, if they exist if "qubit_lo_freq" in qobj_config_dict: qobj_config_dict["qubit_lo_freq"] = [ freq / 1e9 for freq in qobj_config_dict["qubit_lo_freq"] ] if "meas_lo_freq" in qobj_config_dict: qobj_config_dict["meas_lo_freq"] = [ freq / 1e9 for freq in qobj_config_dict["meas_lo_freq"] ] # override default los if single ``schedule_los`` entry set schedule_los = qobj_config_dict.pop("schedule_los", []) if len(schedule_los) == 1: lo_dict = schedule_los[0] q_los = lo_converter.get_qubit_los(lo_dict) # Hz -> GHz if q_los: qobj_config_dict["qubit_lo_freq"] = [ freq / 1e9 for freq in q_los ] m_los = lo_converter.get_meas_los(lo_dict) if m_los: qobj_config_dict["meas_lo_freq"] = [ freq / 1e9 for freq in m_los ] qobj_config = QasmQobjConfig(**qobj_config_dict) qubit_sizes = [] memory_slot_sizes = [] for circ in circuits: num_qubits = 0 memory_slots = 0 for qreg in circ.qregs: num_qubits += qreg.size for creg in circ.cregs: memory_slots += creg.size qubit_sizes.append(num_qubits) memory_slot_sizes.append(memory_slots) qobj_config.memory_slots = max(memory_slot_sizes) qobj_config.n_qubits = max(qubit_sizes) if pulse_library: qobj_config.pulse_library = [ PulseLibraryItem(name=name, samples=samples) for name, samples in pulse_library.items() ] if calibrations and calibrations.gates: qobj_config.calibrations = calibrations return QasmQobj(qobj_id=qobj_id, config=qobj_config, experiments=experiments, header=qobj_header)
def test_to_dict_per_class(self): """Test converting from Qobj and its subclass representations given a dictionary.""" test_parameters = { PulseQobj: (self.valid_qobj, self.valid_dict), PulseQobjConfig: ( PulseQobjConfig( meas_level=1, memory_slot_size=8192, meas_return="avg", pulse_library=[ PulseLibraryItem(name="pulse0", samples=[0.1 + 0.0j]) ], qubit_lo_freq=[4.9], meas_lo_freq=[6.9], rep_time=1000, ), { "meas_level": 1, "memory_slot_size": 8192, "meas_return": "avg", "pulse_library": [{ "name": "pulse0", "samples": [0.1 + 0j] }], "qubit_lo_freq": [4.9], "meas_lo_freq": [6.9], "rep_time": 1000, }, ), PulseLibraryItem: ( PulseLibraryItem(name="pulse0", samples=[0.1 + 0.0j]), { "name": "pulse0", "samples": [0.1 + 0j] }, ), PulseQobjExperiment: ( PulseQobjExperiment(instructions=[ PulseQobjInstruction(name="pulse0", t0=0, ch="d0") ]), { "instructions": [{ "name": "pulse0", "t0": 0, "ch": "d0" }] }, ), PulseQobjInstruction: ( PulseQobjInstruction(name="pulse0", t0=0, ch="d0"), { "name": "pulse0", "t0": 0, "ch": "d0" }, ), } for qobj_class, (qobj_item, expected_dict) in test_parameters.items(): with self.subTest(msg=str(qobj_class)): self.assertEqual(qobj_item.to_dict(), expected_dict)
def setUp(self): super().setUp() self.valid_qobj = PulseQobj( qobj_id="12345", header=QobjHeader(), config=PulseQobjConfig( shots=1024, memory_slots=2, max_credits=10, meas_level=1, memory_slot_size=8192, meas_return="avg", pulse_library=[ PulseLibraryItem( name="pulse0", samples=[0.0 + 0.0j, 0.5 + 0.0j, 0.0 + 0.0j]) ], qubit_lo_freq=[4.9], meas_lo_freq=[6.9], rep_time=1000, ), experiments=[ PulseQobjExperiment(instructions=[ PulseQobjInstruction(name="pulse0", t0=0, ch="d0"), PulseQobjInstruction(name="fc", t0=5, ch="d0", phase=1.57), PulseQobjInstruction(name="fc", t0=5, ch="d0", phase=0.0), PulseQobjInstruction(name="fc", t0=5, ch="d0", phase="P1"), PulseQobjInstruction( name="setp", t0=10, ch="d0", phase=3.14), PulseQobjInstruction( name="setf", t0=10, ch="d0", frequency=8.0), PulseQobjInstruction( name="shiftf", t0=10, ch="d0", frequency=4.0), PulseQobjInstruction( name="acquire", t0=15, duration=5, qubits=[0], memory_slot=[0], kernels=[ QobjMeasurementOption(name="boxcar", params={ "start_window": 0, "stop_window": 5 }) ], ), ]) ], ) self.valid_dict = { "qobj_id": "12345", "type": "PULSE", "schema_version": "1.2.0", "header": {}, "config": { "max_credits": 10, "memory_slots": 2, "shots": 1024, "meas_level": 1, "memory_slot_size": 8192, "meas_return": "avg", "pulse_library": [{ "name": "pulse0", "samples": [0, 0.5, 0] }], "qubit_lo_freq": [4.9], "meas_lo_freq": [6.9], "rep_time": 1000, }, "experiments": [{ "instructions": [ { "name": "pulse0", "t0": 0, "ch": "d0" }, { "name": "fc", "t0": 5, "ch": "d0", "phase": 1.57 }, { "name": "fc", "t0": 5, "ch": "d0", "phase": 0 }, { "name": "fc", "t0": 5, "ch": "d0", "phase": "P1" }, { "name": "setp", "t0": 10, "ch": "d0", "phase": 3.14 }, { "name": "setf", "t0": 10, "ch": "d0", "frequency": 8.0 }, { "name": "shiftf", "t0": 10, "ch": "d0", "frequency": 4.0 }, { "name": "acquire", "t0": 15, "duration": 5, "qubits": [0], "memory_slot": [0], "kernels": [{ "name": "boxcar", "params": { "start_window": 0, "stop_window": 5 } }], }, ] }], }
def test_gate_calibrations_to_dict(self): """Test gate calibrations to dict.""" pulse_library = [PulseLibraryItem(name="test", samples=[1j, 1j])] valid_qobj = QasmQobj( qobj_id="12345", header=QobjHeader(), config=QasmQobjConfig(shots=1024, memory_slots=2, max_credits=10, pulse_library=pulse_library), experiments=[ QasmQobjExperiment( instructions=[ QasmQobjInstruction(name="u1", qubits=[1], params=[0.4]) ], config=QasmQobjConfig( calibrations=QasmExperimentCalibrations(gates=[ GateCalibration(name="u1", qubits=[1], params=[0.4], instructions=[]) ])), ) ], ) res = valid_qobj.to_dict() expected_dict = { "qobj_id": "12345", "type": "QASM", "schema_version": "1.3.0", "header": {}, "config": { "max_credits": 10, "memory_slots": 2, "shots": 1024, "pulse_library": [{ "name": "test", "samples": [1j, 1j] }], }, "experiments": [{ "instructions": [{ "name": "u1", "params": [0.4], "qubits": [1] }], "config": { "calibrations": { "gates": [{ "name": "u1", "qubits": [1], "params": [0.4], "instructions": [] }] } }, "header": {}, }], } self.assertEqual(expected_dict, res)
def test_gate_calibrations_to_dict(self): """Test gate calibrations to dict.""" pulse_library = [PulseLibraryItem(name='test', samples=[1j, 1j])] valid_qobj = QasmQobj( qobj_id='12345', header=QobjHeader(), config=QasmQobjConfig(shots=1024, memory_slots=2, max_credits=10, pulse_library=pulse_library), experiments=[ QasmQobjExperiment( instructions=[ QasmQobjInstruction(name='u1', qubits=[1], params=[0.4]) ], config=QasmQobjConfig( calibrations=QasmExperimentCalibrations(gates=[ GateCalibration(name='u1', qubits=[1], params=[0.4], instructions=[]) ]))) ]) res = valid_qobj.to_dict(validate=True) expected_dict = { 'qobj_id': '12345', 'type': 'QASM', 'schema_version': '1.3.0', 'header': {}, 'config': { 'max_credits': 10, 'memory_slots': 2, 'shots': 1024, 'pulse_library': [{ 'name': 'test', 'samples': [1j, 1j] }] }, 'experiments': [{ 'instructions': [{ 'name': 'u1', 'params': [0.4], 'qubits': [1] }], 'config': { 'calibrations': { 'gates': [{ 'name': 'u1', 'qubits': [1], 'params': [0.4], 'instructions': [] }] } }, 'header': {} }], } self.assertEqual(expected_dict, res)
def _assemble_experiments( schedules: List[Schedule], lo_converter: LoConfigConverter, run_config: RunConfig ) -> Tuple[List[PulseQobjExperiment], Dict[str, Any]]: """Assembles a list of schedules into PulseQobjExperiments, and returns related metadata that will be assembled into the Qobj configuration. Args: schedules: Schedules to assemble. lo_converter: The configured frequency converter and validator. run_config: Configuration of the runtime environment. Returns: The list of assembled experiments, and the dictionary of related experiment config. Raises: QiskitError: when frequency settings are not compatible with the experiments. """ freq_configs = [ lo_converter(lo_dict) for lo_dict in getattr(run_config, 'schedule_los', []) ] if len(schedules) > 1 and len(freq_configs) not in [0, 1, len(schedules)]: raise QiskitError( 'Invalid frequency setting is specified. If the frequency is specified, ' 'it should be configured the same for all schedules, configured for each ' 'schedule, or a list of frequencies should be provided for a single ' 'frequency sweep schedule.') instruction_converter = getattr(run_config, 'instruction_converter', InstructionToQobjConverter) instruction_converter = instruction_converter(PulseQobjInstruction, **run_config.to_dict()) compressed_schedules = reschedule.compress_pulses(schedules) user_pulselib = {} experiments = [] for idx, schedule in enumerate(compressed_schedules): qobj_instructions, max_memory_slot = _assemble_instructions( schedule, instruction_converter, run_config, user_pulselib) # TODO: add other experimental header items (see circuit assembler) qobj_experiment_header = QobjExperimentHeader( memory_slots=max_memory_slot + 1, # Memory slots are 0 indexed name=schedule.name or 'Experiment-%d' % idx) experiment = PulseQobjExperiment(header=qobj_experiment_header, instructions=qobj_instructions) if freq_configs: # This handles the cases where one frequency setting applies to all experiments and # where each experiment has a different frequency freq_idx = idx if len(freq_configs) != 1 else 0 experiment.config = freq_configs[freq_idx] experiments.append(experiment) # Frequency sweep if freq_configs and len(experiments) == 1: experiment = experiments[0] experiments = [] for freq_config in freq_configs: experiments.append( PulseQobjExperiment(header=experiment.header, instructions=experiment.instructions, config=freq_config)) # Top level Qobj configuration experiment_config = { 'pulse_library': [ PulseLibraryItem(name=name, samples=samples) for name, samples in user_pulselib.items() ], 'memory_slots': max([exp.header.memory_slots for exp in experiments]) } return experiments, experiment_config
def assemble_schedules(schedules, qobj_id, qobj_header, run_config): """Assembles a list of schedules into a qobj which can be run on the backend. Args: schedules (list[Schedule]): schedules to assemble qobj_id (int): identifier for the generated qobj qobj_header (QobjHeader): header to pass to the results run_config (RunConfig): configuration of the runtime environment Returns: PulseQobj: the Qobj to be run on the backends Raises: QiskitError: when invalid schedules or configs are provided """ if hasattr(run_config, 'instruction_converter'): instruction_converter = run_config.instruction_converter else: instruction_converter = InstructionToQobjConverter qobj_config = run_config.to_dict() qubit_lo_range = qobj_config.pop('qubit_lo_range') meas_lo_range = qobj_config.pop('meas_lo_range') meas_map = qobj_config.pop('meas_map', None) instruction_converter = instruction_converter(PulseQobjInstruction, **qobj_config) lo_converter = LoConfigConverter(PulseQobjExperimentConfig, qubit_lo_range=qubit_lo_range, meas_lo_range=meas_lo_range, **qobj_config) # Pack everything into the Qobj qobj_schedules = [] user_pulselib = set() for idx, schedule in enumerate(schedules): # instructions qobj_instructions = [] # Instructions are returned as tuple of shifted time and instruction for shift, instruction in schedule.instructions: # TODO: support conditional gate qobj_instructions.append(instruction_converter(shift, instruction)) if isinstance(instruction, PulseInstruction): # add samples to pulse library user_pulselib.add(instruction.command) if isinstance(instruction, AcquireInstruction): if meas_map: # verify all acquires satisfy meas_map _validate_meas_map(instruction, meas_map) # experiment header qobj_experiment_header = QobjExperimentHeader( name=schedule.name or 'Experiment-%d' % idx ) qobj_schedules.append({ 'header': qobj_experiment_header, 'instructions': qobj_instructions }) # setup pulse_library qobj_config['pulse_library'] = [PulseLibraryItem(name=pulse.name, samples=pulse.samples) for pulse in user_pulselib] # create qobj experiment field experiments = [] schedule_los = qobj_config.pop('schedule_los', []) if len(schedule_los) == 1: lo_dict = schedule_los[0] # update global config q_los = lo_converter.get_qubit_los(lo_dict) if q_los: qobj_config['qubit_lo_freq'] = q_los m_los = lo_converter.get_meas_los(lo_dict) if m_los: qobj_config['meas_lo_freq'] = m_los if schedule_los: # multiple frequency setups if len(qobj_schedules) == 1: # frequency sweep for lo_dict in schedule_los: experiments.append(PulseQobjExperiment( instructions=qobj_schedules[0]['instructions'], header=qobj_schedules[0]['header'], config=lo_converter(lo_dict) )) elif len(qobj_schedules) == len(schedule_los): # n:n setup for lo_dict, schedule in zip(schedule_los, qobj_schedules): experiments.append(PulseQobjExperiment( instructions=schedule['instructions'], header=schedule['header'], config=lo_converter(lo_dict) )) else: raise QiskitError('Invalid LO setting is specified. ' 'The LO should be configured for each schedule, or ' 'single setup for all schedules (unique), or ' 'multiple setups for a single schedule (frequency sweep),' 'or no LO configured at all.') else: # unique frequency setup for schedule in qobj_schedules: experiments.append(PulseQobjExperiment( instructions=schedule['instructions'], header=schedule['header'], )) qobj_config = PulseQobjConfig(**qobj_config) return PulseQobj(qobj_id=qobj_id, config=qobj_config, experiments=experiments, header=qobj_header)
def assemble_schedules(schedules, qobj_id, qobj_header, run_config): """Assembles a list of schedules into a qobj which can be run on the backend. Args: schedules (list[Schedule]): schedules to assemble qobj_id (int): identifier for the generated qobj qobj_header (QobjHeader): header to pass to the results run_config (RunConfig): configuration of the runtime environment Returns: PulseQobj: the Qobj to be run on the backends Raises: QiskitError: when invalid schedules or configs are provided """ if hasattr(run_config, 'instruction_converter'): instruction_converter = run_config.instruction_converter else: instruction_converter = InstructionToQobjConverter qobj_config = run_config.to_dict() qubit_lo_freq = qobj_config.get('qubit_lo_freq', None) if qubit_lo_freq is None: raise QiskitError('qubit_lo_freq must be supplied.') meas_lo_freq = qobj_config.get('meas_lo_freq', None) if meas_lo_freq is None: raise QiskitError('meas_lo_freq must be supplied.') qubit_lo_range = qobj_config.pop('qubit_lo_range', None) meas_lo_range = qobj_config.pop('meas_lo_range', None) meas_map = qobj_config.pop('meas_map', None) # convert enums to serialized values meas_return = qobj_config.get('meas_return', 'avg') if isinstance(meas_return, MeasReturnType): qobj_config['meas_return'] = meas_return.value meas_level = qobj_config.get('meas_return', 2) if isinstance(meas_level, MeasLevel): qobj_config['meas_level'] = meas_level.value instruction_converter = instruction_converter(PulseQobjInstruction, **qobj_config) lo_converter = LoConfigConverter(PulseQobjExperimentConfig, qubit_lo_range=qubit_lo_range, meas_lo_range=meas_lo_range, **qobj_config) memory_slot_size = 0 # Pack everything into the Qobj qobj_schedules = [] user_pulselib = {} for idx, schedule in enumerate(schedules): # instructions max_memory_slot = 0 qobj_instructions = [] # Instructions are returned as tuple of shifted time and instruction for shift, instruction in schedule.instructions: # TODO: support conditional gate if isinstance(instruction, DelayInstruction): # delay instructions are ignored as timing is explicit within qobj continue elif isinstance(instruction, PulseInstruction): name = instruction.command.name if name in user_pulselib and instruction.command != user_pulselib[name]: name = "{0}-{1:x}".format(name, hash(instruction.command.samples.tostring())) instruction = PulseInstruction( command=SamplePulse(name=name, samples=instruction.command.samples), name=instruction.name, channel=instruction.channels[0]) # add samples to pulse library user_pulselib[name] = instruction.command elif isinstance(instruction, AcquireInstruction): max_memory_slot = max(max_memory_slot, *[slot.index for slot in instruction.mem_slots]) if meas_map: # verify all acquires satisfy meas_map _validate_meas_map(instruction, meas_map) converted_instruction = instruction_converter(shift, instruction) qobj_instructions.append(converted_instruction) # memory slot size is memory slot index + 1 because index starts from zero exp_memory_slot_size = max_memory_slot + 1 memory_slot_size = max(memory_slot_size, exp_memory_slot_size) # experiment header # TODO: add other experimental header items (see circuit assembler) qobj_experiment_header = QobjExperimentHeader( memory_slots=exp_memory_slot_size, name=schedule.name or 'Experiment-%d' % idx ) qobj_schedules.append({ 'header': qobj_experiment_header, 'instructions': qobj_instructions }) # set number of memoryslots qobj_config['memory_slots'] = memory_slot_size # setup pulse_library qobj_config['pulse_library'] = [PulseLibraryItem(name=pulse.name, samples=pulse.samples) for pulse in user_pulselib.values()] # create qobj experiment field experiments = [] schedule_los = qobj_config.pop('schedule_los', []) if len(schedule_los) == 1: lo_dict = schedule_los[0] # update global config q_los = lo_converter.get_qubit_los(lo_dict) if q_los: qobj_config['qubit_lo_freq'] = q_los m_los = lo_converter.get_meas_los(lo_dict) if m_los: qobj_config['meas_lo_freq'] = m_los if schedule_los: # multiple frequency setups if len(qobj_schedules) == 1: # frequency sweep for lo_dict in schedule_los: experiments.append(PulseQobjExperiment( instructions=qobj_schedules[0]['instructions'], header=qobj_schedules[0]['header'], config=lo_converter(lo_dict) )) elif len(qobj_schedules) == len(schedule_los): # n:n setup for lo_dict, schedule in zip(schedule_los, qobj_schedules): experiments.append(PulseQobjExperiment( instructions=schedule['instructions'], header=schedule['header'], config=lo_converter(lo_dict) )) else: raise QiskitError('Invalid LO setting is specified. ' 'The LO should be configured for each schedule, or ' 'single setup for all schedules (unique), or ' 'multiple setups for a single schedule (frequency sweep),' 'or no LO configured at all.') else: # unique frequency setup for schedule in qobj_schedules: experiments.append(PulseQobjExperiment( instructions=schedule['instructions'], header=schedule['header'], )) qobj_config = PulseQobjConfig(**qobj_config) return PulseQobj(qobj_id=qobj_id, config=qobj_config, experiments=experiments, header=qobj_header)
def __init__(self): configuration = PulseBackendConfiguration( backend_name='fake_openpulse_2q', backend_version='0.0.0', n_qubits=2, meas_levels=[0, 1, 2], basis_gates=['u1', 'u2', 'u3', 'cx', 'id'], simulator=False, local=True, conditional=True, open_pulse=True, memory=False, max_shots=65536, gates=[GateConfig(name='TODO', parameters=[], qasm_def='TODO')], coupling_map=[[0, 1]], n_registers=2, n_uchannels=2, u_channel_lo=[[UchannelLO(q=0, scale=1. + 0.j)], [ UchannelLO(q=0, scale=-1. + 0.j), UchannelLO(q=1, scale=1. + 0.j) ]], meas_level=[1, 2], qubit_lo_range=[[4.5, 5.5], [4.5, 5.5]], meas_lo_range=[[6.0, 7.0], [6.0, 7.0]], dt=1.3333, dtm=10.5, rep_times=[100, 250, 500, 1000], meas_map=[[0, 1]], channel_bandwidth=[[-0.2, 0.4], [-0.3, 0.3], [-0.3, 0.3], [-0.02, 0.02], [-0.02, 0.02], [-0.02, 0.02]], meas_kernels=['kernel1'], discriminators=['max_1Q_fidelity'], acquisition_latency=[[100, 100], [100, 100]], conditional_latency=[[100, 1000], [1000, 100], [100, 1000], [1000, 100], [100, 1000], [1000, 100]], hamiltonian={ 'h_str': [ "np.pi*(2*v0-alpha0)*O0", "np.pi*alpha0*O0*O0", "2*np.pi*r*X0||D0", "2*np.pi*r*X0||U1", "2*np.pi*r*X1||U0", "np.pi*(2*v1-alpha1)*O1", "np.pi*alpha1*O1*O1", "2*np.pi*r*X1||D1", "2*np.pi*j*(Sp0*Sm1+Sm0*Sp1)" ], 'description': "A hamiltonian for a mocked 2Q device, with 1Q and 2Q terms.", 'qub': { '0': 3, '1': 3 }, 'vars': { 'v0': 5.00, 'v1': 5.1, 'j': 0.01, 'r': 0.02, 'alpha0': -0.33, 'alpha1': -0.33 } }) self._defaults = PulseDefaults( qubit_freq_est=[4.9, 5.0], meas_freq_est=[6.5, 6.6], buffer=10, pulse_library=[ PulseLibraryItem(name='test_pulse_1', samples=[0.j, 0.1j]), PulseLibraryItem(name='test_pulse_2', samples=[0.j, 0.1j, 1j]), PulseLibraryItem(name='test_pulse_3', samples=[0.j, 0.1j, 1j, 0.5 + 0j]), PulseLibraryItem(name='test_pulse_4', samples=7 * [0.j, 0.1j, 1j, 0.5 + 0j]) ], cmd_def=[ Command(name='u1', qubits=[0], sequence=[ PulseQobjInstruction(name='fc', ch='d0', t0=0, phase='-P1*np.pi') ]), Command(name='u1', qubits=[1], sequence=[ PulseQobjInstruction(name='fc', ch='d1', t0=0, phase='-P1*np.pi') ]), Command(name='u2', qubits=[0], sequence=[ PulseQobjInstruction(name='fc', ch='d0', t0=0, phase='-P0*np.pi'), PulseQobjInstruction(name='test_pulse_4', ch='d0', t0=0), PulseQobjInstruction(name='fc', ch='d0', t0=0, phase='-P1*np.pi') ]), Command(name='u2', qubits=[1], sequence=[ PulseQobjInstruction(name='fc', ch='d1', t0=0, phase='-P0*np.pi'), PulseQobjInstruction(name='test_pulse_4', ch='d1', t0=0), PulseQobjInstruction(name='fc', ch='d1', t0=0, phase='-P0*np.pi') ]), Command(name='u3', qubits=[0], sequence=[ PulseQobjInstruction(name='test_pulse_1', ch='d0', t0=0) ]), Command(name='u3', qubits=[1], sequence=[ PulseQobjInstruction(name='test_pulse_3', ch='d1', t0=0) ]), Command(name='cx', qubits=[0, 1], sequence=[ PulseQobjInstruction(name='test_pulse_1', ch='d0', t0=0), PulseQobjInstruction(name='test_pulse_2', ch='u0', t0=10), PulseQobjInstruction(name='test_pulse_1', ch='d1', t0=20), PulseQobjInstruction(name='fc', ch='d1', t0=20, phase=2.1) ]), Command(name='ParametrizedGate', qubits=[0, 1], sequence=[ PulseQobjInstruction(name='test_pulse_1', ch='d0', t0=0), PulseQobjInstruction(name='test_pulse_2', ch='u0', t0=10), PulseQobjInstruction(name='pv', ch='d1', t0=2, val='cos(P2)'), PulseQobjInstruction(name='test_pulse_1', ch='d1', t0=20), PulseQobjInstruction(name='fc', ch='d1', t0=20, phase=2.1) ]), Command(name='measure', qubits=[0, 1], sequence=[ PulseQobjInstruction(name='test_pulse_1', ch='m0', t0=0), PulseQobjInstruction(name='test_pulse_1', ch='m1', t0=0), PulseQobjInstruction(name='acquire', duration=10, t0=0, qubits=[0, 1], memory_slot=[0, 1]) ]) ]) mock_time = datetime.datetime.now() dt = 1.3333 # pylint: disable=invalid-name self._properties = BackendProperties( backend_name='fake_openpulse_2q', backend_version='0.0.0', last_update_date=mock_time, qubits=[[ Nduv(date=mock_time, name='T1', unit='µs', value=71.9500421005539), Nduv(date=mock_time, name='frequency', unit='MHz', value=4919.96800692) ], [ Nduv(date=mock_time, name='T1', unit='µs', value=81.9500421005539), Nduv(date=mock_time, name='frequency', unit='GHz', value=5.01996800692) ]], gates=[ Gate(gate='u1', name='u1_0', qubits=[0], parameters=[ Nduv(date=mock_time, name='gate_error', unit='', value=1.0), Nduv(date=mock_time, name='gate_length', unit='ns', value=0.) ]), Gate(gate='u3', name='u3_0', qubits=[0], parameters=[ Nduv(date=mock_time, name='gate_error', unit='', value=1.0), Nduv(date=mock_time, name='gate_length', unit='ns', value=2 * dt) ]), Gate(gate='u3', name='u3_1', qubits=[1], parameters=[ Nduv(date=mock_time, name='gate_error', unit='', value=1.0), Nduv(date=mock_time, name='gate_length', unit='ns', value=4 * dt) ]), Gate(gate='cx', name='cx0_1', qubits=[0, 1], parameters=[ Nduv(date=mock_time, name='gate_error', unit='', value=1.0), Nduv(date=mock_time, name='gate_length', unit='ns', value=22 * dt) ]), ], general=[]) super().__init__(configuration)