def test_assemble_memory_slots_for_schedules(self): """Test assembling schedules with different memory slots.""" n_memoryslots = [10, 5, 7] schedules = [] for n_memoryslot in n_memoryslots: schedule = Acquire(5, self.backend_config.acquire(0), mem_slot=pulse.MemorySlot(n_memoryslot - 1)) schedules.append(schedule) qobj = assemble(schedules, qubit_lo_freq=self.default_qubit_lo_freq, meas_lo_freq=self.default_meas_lo_freq, meas_map=[[0], [1]]) validate_qobj_against_schema(qobj) self.assertEqual(qobj.config.memory_slots, max(n_memoryslots)) self.assertEqual(qobj.experiments[0].header.memory_slots, n_memoryslots[0]) self.assertEqual(qobj.experiments[1].header.memory_slots, n_memoryslots[1]) self.assertEqual(qobj.experiments[2].header.memory_slots, n_memoryslots[2])
def test_single_and_deprecated_acquire_styles(self): """Test that acquires are identically combined with Acquires that take a single channel.""" backend = FakeOpenPulse2Q() new_style_schedule = Schedule() acq = Acquire(1200) for i in range(5): new_style_schedule += acq(AcquireChannel(i), MemorySlot(i)) deprecated_style_schedule = Schedule() deprecated_style_schedule += acq([AcquireChannel(i) for i in range(5)], [MemorySlot(i) for i in range(5)]) # The Qobj IDs will be different n_qobj = assemble(new_style_schedule, backend) n_qobj.qobj_id = None n_qobj.experiments[0].header.name = None d_qobj = assemble(deprecated_style_schedule, backend) d_qobj.qobj_id = None d_qobj.experiments[0].header.name = None self.assertEqual(n_qobj, d_qobj) assembled_acquire = n_qobj.experiments[0].instructions[0] self.assertEqual(assembled_acquire.qubits, [0, 1, 2, 3, 4]) self.assertEqual(assembled_acquire.memory_slot, [0, 1, 2, 3, 4])
def test_can_construct_valid_acquire_command(self): """Test if valid acquire command can be constructed.""" kernel_opts = {'start_window': 0, 'stop_window': 10} kernel = Kernel(name='boxcar', **kernel_opts) discriminator_opts = { 'neighborhoods': [{ 'qubits': 1, 'channels': 1 }], 'cal': 'coloring', 'resample': False } discriminator = Discriminator(name='linear_discriminator', **discriminator_opts) acq = Acquire(duration=10, kernel=kernel, discriminator=discriminator) self.assertEqual(acq.duration, 10) self.assertEqual(acq.discriminator.name, 'linear_discriminator') self.assertEqual(acq.discriminator.params, discriminator_opts) self.assertEqual(acq.kernel.name, 'boxcar') self.assertEqual(acq.kernel.params, kernel_opts) self.assertTrue(acq.name.startswith('acq'))
def test_measure_combined(self): """ Test to check for measure on the same qubit which generated another measure schedule. The measures on different qubits are combined, but measures on the same qubit adds another measure to the schedule. """ q = QuantumRegister(2) c = ClassicalRegister(2) qc = QuantumCircuit(q, c) qc.u2(3.14, 1.57, q[0]) qc.cx(q[0], q[1]) qc.measure(q[0], c[0]) qc.measure(q[1], c[1]) qc.measure(q[1], c[1]) sched = schedule(qc, self.backend, method="as_soon_as_possible") expected = Schedule( self.cmd_def.get('u2', [0], 3.14, 1.57), (28, self.cmd_def.get('cx', [0, 1])), (50, self.cmd_def.get('measure', [0, 1])), (60, self.cmd_def.get('measure', [0, 1]).filter(channels=[MeasureChannel(1)])), (60, Acquire(duration=10)([AcquireChannel(0), AcquireChannel(1)], [MemorySlot(0), MemorySlot(1)]))) self.assertEqual(sched.instructions, expected.instructions)
def _3Q_constant_sched(self, total_samples, amp=1., u_idx=0, subsystem_list=[0, 2]): """Creates a runnable schedule for the 3Q system after the system is restricted to 2 qubits. Args: total_samples (int): length of pulse amp (float): amplitude of constant pulse (can be complex) u_idx (int): index of U channel subsystem_list (list): list of qubits to restrict to Returns: schedule (pulse schedule): schedule with a drive pulse followed by an acquire """ # set up constant pulse for doing a pi pulse drive_pulse = SamplePulse(amp * np.ones(total_samples)) schedule = Schedule() schedule |= Play(drive_pulse, ControlChannel(u_idx)) for idx in subsystem_list: schedule |= Acquire(total_samples, AcquireChannel(idx), MemorySlot(idx)) << total_samples return schedule
def test_measure_combined(self): """ Test to check for measure on the same qubit which generated another measure schedule. The measures on different qubits are combined, but measures on the same qubit adds another measure to the schedule. """ q = QuantumRegister(2) c = ClassicalRegister(2) qc = QuantumCircuit(q, c) qc.append(U2Gate(3.14, 1.57), [q[0]]) qc.cx(q[0], q[1]) qc.measure(q[0], c[0]) qc.measure(q[1], c[1]) qc.measure(q[1], c[1]) sched = schedule(qc, self.backend, method="as_soon_as_possible") expected = Schedule( self.inst_map.get("u2", [0], 3.14, 1.57), (2, self.inst_map.get("cx", [0, 1])), (24, self.inst_map.get("measure", [0, 1])), (34, self.inst_map.get("measure", [0, 1]).filter(channels=[MeasureChannel(1)])), (34, Acquire(10, AcquireChannel(1), MemorySlot(1))), ) self.assertEqual(sched.instructions, expected.instructions)
def test_schedule_with_acquire_for_back_and_forward_compatibility(self): """Test schedule with acquire for back and forward compatibility.""" dur = 10 with self.assertWarns(DeprecationWarning): # mem_slots and reg_slots are deprecated kwargs cmds = [ Acquire(dur, AcquireChannel(0), MemorySlot(0)), Acquire(dur, [AcquireChannel(0)], MemorySlot(0)), Acquire(dur, AcquireChannel(0), [MemorySlot(0)]), Acquire(dur, [AcquireChannel(0)], mem_slots=[MemorySlot(0)]), Acquire(dur, AcquireChannel(0), MemorySlot(0), [RegisterSlot(0)]), Acquire(dur, AcquireChannel(0), MemorySlot(0), reg_slot=RegisterSlot(0)) ] for cmd in cmds: mixed_schedule = Schedule() mixed_schedule = mixed_schedule.insert(dur, cmd) self.assertEqual(len(mixed_schedule.instructions), 1) self.assertTrue(MemorySlot(0) in mixed_schedule.channels)
def measure(qubits: List[int], backend=None, inst_map: Optional[InstructionScheduleMap] = None, meas_map: Optional[Union[List[List[int]], Dict[int, List[int]]]] = None, qubit_mem_slots: Optional[Dict[int, int]] = None, measure_name: str = 'measure') -> Schedule: """ Return a schedule which measures the requested qubits according to the given instruction mapping and measure map, or by using the defaults provided by the backend. By default, the measurement results for each qubit are trivially mapped to the qubit index. This behavior is overridden by qubit_mem_slots. For instance, to measure qubit 0 into MemorySlot(1), qubit_mem_slots can be provided as {0: 1}. Args: qubits: List of qubits to be measured. backend (BaseBackend): A backend instance, which contains hardware-specific data required for scheduling. inst_map: Mapping of circuit operations to pulse schedules. If None, defaults to the ``instruction_schedule_map`` of ``backend``. meas_map: List of sets of qubits that must be measured together. If None, defaults to the ``meas_map`` of ``backend``. qubit_mem_slots: Mapping of measured qubit index to classical bit index. measure_name: Name of the measurement schedule. Returns: A measurement schedule corresponding to the inputs provided. Raises: PulseError: If both ``inst_map`` or ``meas_map``, and ``backend`` is None. """ schedule = Schedule( name="Default measurement schedule for qubits {}".format(qubits)) try: inst_map = inst_map or backend.defaults().instruction_schedule_map meas_map = meas_map or backend.configuration().meas_map except AttributeError: raise PulseError( 'inst_map or meas_map, and backend cannot be None simultaneously') if isinstance(meas_map, List): meas_map = format_meas_map(meas_map) measure_groups = set() for qubit in qubits: measure_groups.add(tuple(meas_map[qubit])) for measure_group_qubits in measure_groups: if qubit_mem_slots is not None: unused_mem_slots = set(measure_group_qubits) - set( qubit_mem_slots.values()) try: default_sched = inst_map.get(measure_name, measure_group_qubits) except PulseError: raise PulseError( "We could not find a default measurement schedule called '{}'. " "Please provide another name using the 'measure_name' keyword " "argument. For assistance, the instructions which are defined are: " "{}".format(measure_name, inst_map.instructions)) for time, inst in default_sched.instructions: if qubit_mem_slots and isinstance(inst, (Acquire, AcquireInstruction)): if inst.channel.index in qubit_mem_slots: mem_slot = MemorySlot(qubit_mem_slots[inst.channel.index]) else: mem_slot = MemorySlot(unused_mem_slots.pop()) schedule = schedule.insert( time, Acquire(inst.duration, inst.channel, mem_slot=mem_slot)) elif qubit_mem_slots is None and isinstance( inst, (Acquire, AcquireInstruction)): schedule = schedule.insert(time, inst) # Measurement pulses should only be added if its qubit was measured by the user elif inst.channels[0].index in qubits: schedule = schedule.insert(time, inst) return schedule
def test_align_measures(self): """Test that one acquire is delayed to match the time of the later acquire.""" sched = pulse.Schedule(name='fake_experiment') sched.insert(0, Play(self.short_pulse, self.config.drive(0)), inplace=True) sched.insert(1, Acquire(5, self.config.acquire(0), MemorySlot(0)), inplace=True) sched.insert(10, Acquire(5, self.config.acquire(1), MemorySlot(1)), inplace=True) sched.insert(10, Play(self.short_pulse, self.config.measure(0)), inplace=True) sched.insert(11, Play(self.short_pulse, self.config.measure(0)), inplace=True) sched.insert(10, Play(self.short_pulse, self.config.measure(1)), inplace=True) aligned = transforms.align_measures([sched])[0] self.assertEqual(aligned.name, 'fake_experiment') ref = pulse.Schedule(name='fake_experiment') ref.insert(0, Play(self.short_pulse, self.config.drive(0)), inplace=True) ref.insert(10, Acquire(5, self.config.acquire(0), MemorySlot(0)), inplace=True) ref.insert(10, Acquire(5, self.config.acquire(1), MemorySlot(1)), inplace=True) ref.insert(19, Play(self.short_pulse, self.config.measure(0)), inplace=True) ref.insert(20, Play(self.short_pulse, self.config.measure(0)), inplace=True) ref.insert(10, Play(self.short_pulse, self.config.measure(1)), inplace=True) self.assertEqual(aligned, ref) aligned = transforms.align_measures([sched], self.inst_map, align_time=20)[0] ref = pulse.Schedule(name='fake_experiment') ref.insert(10, Play(self.short_pulse, self.config.drive(0)), inplace=True) ref.insert(20, Acquire(5, self.config.acquire(0), MemorySlot(0)), inplace=True) ref.insert(20, Acquire(5, self.config.acquire(1), MemorySlot(1)), inplace=True) ref.insert(29, Play(self.short_pulse, self.config.measure(0)), inplace=True) ref.insert(30, Play(self.short_pulse, self.config.measure(0)), inplace=True) ref.insert(20, Play(self.short_pulse, self.config.measure(1)), inplace=True) self.assertEqual(aligned, ref)
def test_filter_inst_types(self): """Test filtering on instruction types.""" lp0 = self.linear(duration=3, slope=0.2, intercept=0.1) sched = Schedule(name='fake_experiment') sched = sched.insert(0, Play(lp0, self.config.drive(0))) sched = sched.insert(10, Play(lp0, self.config.drive(1))) sched = sched.insert(30, ShiftPhase(-1.57, self.config.drive(0))) sched = sched.insert(40, SetFrequency(8.0, self.config.drive(0))) sched = sched.insert(50, ShiftFrequency(4.0e6, self.config.drive(0))) sched = sched.insert(55, SetPhase(3.14, self.config.drive(0))) for i in range(2): sched = sched.insert( 60, Acquire(5, self.config.acquire(i), MemorySlot(i))) sched = sched.insert(90, Play(lp0, self.config.drive(0))) # test on Acquire only_acquire, no_acquire = \ self._filter_and_test_consistency(sched, instruction_types=[Acquire]) for _, inst in only_acquire.instructions: self.assertIsInstance(inst, Acquire) for _, inst in no_acquire.instructions: self.assertFalse(isinstance(inst, Acquire)) # test two instruction types only_pulse_and_fc, no_pulse_and_fc = \ self._filter_and_test_consistency(sched, instruction_types=[Play, ShiftPhase]) for _, inst in only_pulse_and_fc.instructions: self.assertIsInstance(inst, (Play, ShiftPhase)) for _, inst in no_pulse_and_fc.instructions: self.assertFalse(isinstance(inst, (Play, ShiftPhase))) self.assertEqual(len(only_pulse_and_fc.instructions), 4) self.assertEqual(len(no_pulse_and_fc.instructions), 5) # test on ShiftPhase only_fc, no_fc = \ self._filter_and_test_consistency(sched, instruction_types={ShiftPhase}) self.assertEqual(len(only_fc.instructions), 1) self.assertEqual(len(no_fc.instructions), 8) # test on SetPhase only_setp, no_setp = \ self._filter_and_test_consistency(sched, instruction_types={SetPhase}) self.assertEqual(len(only_setp.instructions), 1) self.assertEqual(len(no_setp.instructions), 8) # test on SetFrequency only_setf, no_setf = self._filter_and_test_consistency( sched, instruction_types=[SetFrequency]) for _, inst in only_setf.instructions: self.assertTrue(isinstance(inst, SetFrequency)) self.assertEqual(len(only_setf.instructions), 1) self.assertEqual(len(no_setf.instructions), 8) # test on ShiftFrequency only_shiftf, no_shiftf = \ self._filter_and_test_consistency(sched, instruction_types=[ShiftFrequency]) for _, inst in only_shiftf.instructions: self.assertTrue(isinstance(inst, ShiftFrequency)) self.assertEqual(len(only_shiftf.instructions), 1) self.assertEqual(len(no_shiftf.instructions), 8)
def my_test_make_schedule(acquire: int, memoryslot: int, shift: int): sched1 = Acquire(acquire, AcquireChannel(0), MemorySlot(memoryslot)) sched2 = Acquire(acquire, AcquireChannel(1), MemorySlot(memoryslot)).shift(shift) return Schedule(sched1, sched2)
def test_multiple_channels_out_of_order(self): """Test that schedule with multiple channels equal when out of order.""" instructions = [(0, ShiftPhase(0, DriveChannel(1))), (1, Acquire(10, AcquireChannel(0), MemorySlot(1)))] self.assertEqual(Schedule(*instructions), Schedule(*reversed(instructions)))
def test_shift_phase(self): """Test ShiftPhase command.""" omega_0 = 1.123 r = 1. system_model = self._system_model_1Q(omega_0, r) # run a schedule in which a shifted phase causes a pulse to cancel itself. # Also do it in multiple phase shifts to test accumulation sched = Schedule() amp1 = 0.12 sched += Play(Waveform([amp1]), DriveChannel(0)) phi1 = 0.12374 * np.pi sched += ShiftPhase(phi1, DriveChannel(0)) amp2 = 0.492 sched += Play(Waveform([amp2]), DriveChannel(0)) phi2 = 0.5839 * np.pi sched += ShiftPhase(phi2, DriveChannel(0)) amp3 = 0.12 + 0.21 * 1j sched += Play(Waveform([amp3]), DriveChannel(0)) sched |= Acquire(1, AcquireChannel(0), MemorySlot(0)) << sched.duration y0 = np.array([1., 0]) pulse_sim = PulseSimulator(system_model=system_model, initial_state=y0) qobj = assemble([sched], backend=pulse_sim, meas_level=2, meas_return='single', meas_map=[[0]], qubit_lo_freq=[omega_0], memory_slots=2, shots=1) results = pulse_sim.run(qobj).result() pulse_sim_yf = results.get_statevector() #run independent simulation samples = np.array([[amp1], [amp2 * np.exp(1j * phi1)], [amp3 * np.exp(1j * (phi1 + phi2))]]) indep_yf = simulate_1q_model(y0, omega_0, r, np.array([omega_0]), samples, 1.) self.assertGreaterEqual(state_fidelity(pulse_sim_yf, indep_yf), 1 - (10**-5)) # run another schedule with only a single shift phase to verify sched = Schedule() amp1 = 0.12 sched += Play(Waveform([amp1]), DriveChannel(0)) phi1 = 0.12374 * np.pi sched += ShiftPhase(phi1, DriveChannel(0)) amp2 = 0.492 sched += Play(Waveform([amp2]), DriveChannel(0)) sched |= Acquire(1, AcquireChannel(0), MemorySlot(0)) << sched.duration qobj = assemble([sched], backend=pulse_sim, meas_level=2, meas_return='single', meas_map=[[0]], qubit_lo_freq=[omega_0], memory_slots=2, shots=1) results = pulse_sim.run(qobj).result() pulse_sim_yf = results.get_statevector() #run independent simulation samples = np.array([[amp1], [amp2 * np.exp(1j * phi1)]]) indep_yf = simulate_1q_model(y0, omega_0, r, np.array([omega_0]), samples, 1.) self.assertGreaterEqual(state_fidelity(pulse_sim_yf, indep_yf), 1 - (10**-5))
def test_delay_instruction(self): """Test for delay instruction.""" # construct system model specifically for this hamiltonian = {} hamiltonian['h_str'] = ['0.5*r*X0||D0', '0.5*r*Y0||D1'] hamiltonian['vars'] = {'r': np.pi} hamiltonian['qub'] = {'0': 2} ham_model = HamiltonianModel.from_dict(hamiltonian) u_channel_lo = [] subsystem_list = [0] dt = 1. system_model = PulseSystemModel(hamiltonian=ham_model, u_channel_lo=u_channel_lo, subsystem_list=subsystem_list, dt=dt) # construct a schedule that should result in a unitary -Z if delays are correctly handled # i.e. do a pi rotation about x, sandwiched by pi/2 rotations about y in opposite directions # so that the x rotation is transformed into a z rotation. # if delays are not handled correctly this process should fail sched = Schedule() sched += Play(Waveform([0.5]), DriveChannel(1)) sched += Delay(1, DriveChannel(1)) sched += Play(Waveform([-0.5]), DriveChannel(1)) sched += Delay(1, DriveChannel(0)) sched += Play(Waveform([1.]), DriveChannel(0)) sched |= Acquire(1, AcquireChannel(0), MemorySlot(0)) << sched.duration # Result of schedule should be the unitary -1j*Z, so check rotation of an X eigenstate pulse_sim = PulseSimulator(system_model=system_model, initial_state=np.array([1., 1.]) / np.sqrt(2)) qobj = assemble([sched], backend=pulse_sim, meas_level=2, meas_return='single', meas_map=[[0]], qubit_lo_freq=[0., 0.], memory_slots=2, shots=1) results = pulse_sim.run(qobj).result() statevector = results.get_statevector() expected_vector = np.array([-1j, 1j]) / np.sqrt(2) self.assertGreaterEqual(state_fidelity(statevector, expected_vector), 1 - (10**-5)) # verify validity of simulation when no delays included sched = Schedule() sched += Play(Waveform([0.5]), DriveChannel(1)) sched += Play(Waveform([-0.5]), DriveChannel(1)) sched += Play(Waveform([1.]), DriveChannel(0)) sched |= Acquire(1, AcquireChannel(0), MemorySlot(0)) << sched.duration qobj = assemble([sched], backend=pulse_sim, meas_level=2, meas_return='single', meas_map=[[0]], qubit_lo_freq=[0., 0.], memory_slots=2, shots=1) results = pulse_sim.run(qobj).result() statevector = results.get_statevector() U = expm(1j * np.pi * self.Y / 4) @ expm(-1j * np.pi * (self.Y / 4 + self.X / 2)) expected_vector = U @ np.array([1., 1.]) / np.sqrt(2) self.assertGreaterEqual(state_fidelity(statevector, expected_vector), 1 - (10**-5))
def test_2Q_exchange(self): r"""Test a more complicated 2q simulation""" q_freqs = [5., 5.1] r = 0.02 j = 0.02 total_samples = 25 hamiltonian = {} hamiltonian['h_str'] = [ '2*np.pi*v0*0.5*Z0', '2*np.pi*v1*0.5*Z1', '2*np.pi*r*0.5*X0||D0', '2*np.pi*r*0.5*X1||D1', '2*np.pi*j*0.5*I0*I1', '2*np.pi*j*0.5*X0*X1', '2*np.pi*j*0.5*Y0*Y1', '2*np.pi*j*0.5*Z0*Z1' ] hamiltonian['vars'] = { 'v0': q_freqs[0], 'v1': q_freqs[1], 'r': r, 'j': j } hamiltonian['qub'] = {'0': 2, '1': 2} ham_model = HamiltonianModel.from_dict(hamiltonian) # set the U0 to have frequency of drive channel 0 u_channel_lo = [] subsystem_list = [0, 1] dt = 1. system_model = PulseSystemModel(hamiltonian=ham_model, u_channel_lo=u_channel_lo, subsystem_list=subsystem_list, dt=dt) # try some random schedule schedule = Schedule() drive_pulse = Waveform(np.ones(total_samples)) schedule += Play(drive_pulse, DriveChannel(0)) schedule |= Play(drive_pulse, DriveChannel(1)) << 2 * total_samples schedule |= Acquire(total_samples, AcquireChannel(0), MemorySlot(0)) << 3 * total_samples schedule |= Acquire(total_samples, AcquireChannel(1), MemorySlot(1)) << 3 * total_samples y0 = np.array([1., 0., 0., 0.]) pulse_sim = PulseSimulator(system_model=system_model, initial_state=y0, seed=9000) qobj = assemble([schedule], backend=pulse_sim, meas_level=2, meas_return='single', meas_map=[[0]], qubit_lo_freq=q_freqs, memory_slots=2, shots=1000) result = pulse_sim.run(qobj).result() pulse_sim_yf = result.get_statevector() # set up and run independent simulation d0_samps = np.concatenate( (np.ones(total_samples), np.zeros(2 * total_samples))) d1_samps = np.concatenate( (np.zeros(2 * total_samples), np.ones(total_samples))) samples = np.array([d0_samps, d1_samps]).transpose() q_freqs = np.array(q_freqs) yf = simulate_2q_exchange_model(y0, q_freqs, r, j, q_freqs, samples, 1.) # Check fidelity of statevectors self.assertGreaterEqual(state_fidelity(pulse_sim_yf, yf), 1 - (10**-5))
def test_filter_intervals(self): """Test filtering on intervals.""" lp0 = self.linear(duration=3, slope=0.2, intercept=0.1) sched = Schedule(name="fake_experiment") sched = sched.insert(0, Play(lp0, self.config.drive(0))) sched = sched.insert(10, Play(lp0, self.config.drive(1))) sched = sched.insert(30, ShiftPhase(-1.57, self.config.drive(0))) for i in range(2): sched = sched.insert( 60, Acquire(5, self.config.acquire(i), MemorySlot(i))) sched = sched.insert(90, Play(lp0, self.config.drive(0))) # split schedule into instructions occurring in (0,13), and those outside filtered, excluded = self._filter_and_test_consistency( sched, time_ranges=((0, 13), )) for start_time, inst in filtered.instructions: self.assertTrue((start_time >= 0) and (start_time + inst.stop_time <= 13)) for start_time, inst in excluded.instructions: self.assertFalse((start_time >= 0) and (start_time + inst.stop_time <= 13)) self.assertEqual(len(filtered.instructions), 2) self.assertEqual(len(excluded.instructions), 4) # split into schedule occurring in and outside of interval (59,65) filtered, excluded = self._filter_and_test_consistency(sched, time_ranges=[ (59, 65) ]) self.assertEqual(len(filtered.instructions), 2) self.assertEqual(filtered.instructions[0][0], 60) self.assertIsInstance(filtered.instructions[0][1], Acquire) self.assertEqual(len(excluded.instructions), 4) self.assertEqual(excluded.instructions[3][0], 90) self.assertIsInstance(excluded.instructions[3][1], Play) # split instructions based on the interval # (none should be, though they have some overlap with some of the instructions) filtered, excluded = self._filter_and_test_consistency(sched, time_ranges=[ (0, 2), (8, 11), (61, 70) ]) self.assertEqual(len(filtered.instructions), 0) self.assertEqual(len(excluded.instructions), 6) # split instructions from multiple non-overlapping intervals, specified # as time ranges filtered, excluded = self._filter_and_test_consistency(sched, time_ranges=[ (10, 15), (63, 93) ]) self.assertEqual(len(filtered.instructions), 2) self.assertEqual(len(excluded.instructions), 4) # split instructions from non-overlapping intervals, specified as Intervals filtered, excluded = self._filter_and_test_consistency(sched, intervals=[ (10, 15), (63, 93) ]) self.assertEqual(len(filtered.instructions), 2) self.assertEqual(len(excluded.instructions), 4)