15#ifndef _QCSIMSIMULATOR_H
16#define _QCSIMSIMULATOR_H
18#ifdef INCLUDED_BY_FACTORY
22#define _USE_MATH_DEFINES
31class IndividualSimulator;
44class QCSimSimulator :
public QCSimState {
45 friend class IndividualSimulator;
48 QCSimSimulator() =
default;
50 QCSimSimulator(
const QCSimSimulator &) =
delete;
51 QCSimSimulator &operator=(
const QCSimSimulator &) =
delete;
54 QCSimSimulator(QCSimSimulator &&other) =
default;
55 QCSimSimulator &operator=(QCSimSimulator &&other) =
default;
65 pgate.SetPhaseShift(lambda);
67 mpsSimulator->ApplyGate(pgate,
static_cast<unsigned int>(qubit));
69 if (std::abs(lambda - M_PI_2) > 1e-10)
70 throw std::runtime_error(
71 "QCSimSimulator::ApplyP: Invalid phase shift "
72 "angle for a Clifford gate.");
73 cliffordSimulator->ApplyS(
static_cast<unsigned int>(qubit));
75 tensorNetwork->AddGate(pgate,
static_cast<unsigned int>(qubit));
77 pp->ApplyP(
static_cast<unsigned int>(qubit), lambda);
79 QC::Gates::AppliedGate<> agate(pgate.getRawOperatorMatrix(), qubit);
80 pathIntegralSimulator->ApplyGate(agate);
83 state->ApplyGate(pgate,
static_cast<unsigned int>(qubit));
84 NotifyObservers({qubit});
95 mpsSimulator->ApplyGate(xgate,
static_cast<unsigned int>(qubit));
97 cliffordSimulator->ApplyX(
static_cast<unsigned int>(qubit));
99 tensorNetwork->AddGate(xgate,
static_cast<unsigned int>(qubit));
101 pp->ApplyX(
static_cast<unsigned int>(qubit));
103 QC::Gates::AppliedGate<> agate(xgate.getRawOperatorMatrix(), qubit);
104 pathIntegralSimulator->ApplyGate(agate);
107 state->ApplyGate(xgate,
static_cast<unsigned int>(qubit));
108 NotifyObservers({qubit});
119 mpsSimulator->ApplyGate(ygate,
static_cast<unsigned int>(qubit));
121 cliffordSimulator->ApplyY(
static_cast<unsigned int>(qubit));
123 tensorNetwork->AddGate(ygate,
static_cast<unsigned int>(qubit));
125 pp->ApplyY(
static_cast<unsigned int>(qubit));
127 QC::Gates::AppliedGate<> agate(ygate.getRawOperatorMatrix(), qubit);
128 pathIntegralSimulator->ApplyGate(agate);
131 state->ApplyGate(ygate,
static_cast<unsigned int>(qubit));
132 NotifyObservers({qubit});
143 mpsSimulator->ApplyGate(zgate,
static_cast<unsigned int>(qubit));
145 cliffordSimulator->ApplyZ(
static_cast<unsigned int>(qubit));
147 tensorNetwork->AddGate(zgate,
static_cast<unsigned int>(qubit));
149 pp->ApplyZ(
static_cast<unsigned int>(qubit));
151 QC::Gates::AppliedGate<> agate(zgate.getRawOperatorMatrix(), qubit);
152 pathIntegralSimulator->ApplyGate(agate);
155 state->ApplyGate(zgate,
static_cast<unsigned int>(qubit));
156 NotifyObservers({qubit});
167 mpsSimulator->ApplyGate(h,
static_cast<unsigned int>(qubit));
169 cliffordSimulator->ApplyH(
static_cast<unsigned int>(qubit));
171 tensorNetwork->AddGate(h,
static_cast<unsigned int>(qubit));
173 pp->ApplyH(
static_cast<unsigned int>(qubit));
175 QC::Gates::AppliedGate<> agate(h.getRawOperatorMatrix(), qubit);
176 pathIntegralSimulator->ApplyGate(agate);
179 state->ApplyGate(h,
static_cast<unsigned int>(qubit));
180 NotifyObservers({qubit});
191 mpsSimulator->ApplyGate(sgate,
static_cast<unsigned int>(qubit));
193 cliffordSimulator->ApplyS(
static_cast<unsigned int>(qubit));
195 tensorNetwork->AddGate(sgate,
static_cast<unsigned int>(qubit));
197 pp->ApplyS(
static_cast<unsigned int>(qubit));
199 QC::Gates::AppliedGate<> agate(sgate.getRawOperatorMatrix(), qubit);
200 pathIntegralSimulator->ApplyGate(agate);
203 state->ApplyGate(sgate,
static_cast<unsigned int>(qubit));
204 NotifyObservers({qubit});
215 mpsSimulator->ApplyGate(sdggate,
static_cast<unsigned int>(qubit));
217 cliffordSimulator->ApplySdg(
static_cast<unsigned int>(qubit));
219 tensorNetwork->AddGate(sdggate,
static_cast<unsigned int>(qubit));
221 pp->ApplySDG(
static_cast<unsigned int>(qubit));
223 QC::Gates::AppliedGate<> agate(sdggate.getRawOperatorMatrix(), qubit);
224 pathIntegralSimulator->ApplyGate(agate);
227 state->ApplyGate(sdggate,
static_cast<unsigned int>(qubit));
228 NotifyObservers({qubit});
239 mpsSimulator->ApplyGate(tgate,
static_cast<unsigned int>(qubit));
241 throw std::runtime_error(
242 "QCSimSimulator::ApplyT: The stabilizer simulator does not support "
243 "non-clifford gates.");
245 tensorNetwork->AddGate(tgate,
static_cast<unsigned int>(qubit));
247 pp->ApplyT(
static_cast<unsigned int>(qubit));
249 QC::Gates::AppliedGate<> agate(tgate.getRawOperatorMatrix(), qubit);
250 pathIntegralSimulator->ApplyGate(agate);
253 state->ApplyGate(tgate,
static_cast<unsigned int>(qubit));
254 NotifyObservers({qubit});
265 mpsSimulator->ApplyGate(tdggate,
static_cast<unsigned int>(qubit));
267 throw std::runtime_error(
268 "QCSimSimulator::ApplyTDG: The stabilizer simulator does not support "
269 "non-clifford gates.");
271 tensorNetwork->AddGate(tdggate,
static_cast<unsigned int>(qubit));
273 pp->ApplyTDG(
static_cast<unsigned int>(qubit));
275 QC::Gates::AppliedGate<> agate(tdggate.getRawOperatorMatrix(), qubit);
276 pathIntegralSimulator->ApplyGate(agate);
279 state->ApplyGate(tdggate,
static_cast<unsigned int>(qubit));
280 NotifyObservers({qubit});
291 mpsSimulator->ApplyGate(sxgate,
static_cast<unsigned int>(qubit));
293 cliffordSimulator->ApplySx(
static_cast<unsigned int>(qubit));
295 tensorNetwork->AddGate(sxgate,
static_cast<unsigned int>(qubit));
297 pp->ApplySX(
static_cast<unsigned int>(qubit));
299 QC::Gates::AppliedGate<> agate(sxgate.getRawOperatorMatrix(), qubit);
300 pathIntegralSimulator->ApplyGate(agate);
303 state->ApplyGate(sxgate,
static_cast<unsigned int>(qubit));
304 NotifyObservers({qubit});
315 mpsSimulator->ApplyGate(sxdaggate,
static_cast<unsigned int>(qubit));
317 cliffordSimulator->ApplySxDag(
static_cast<unsigned int>(qubit));
319 tensorNetwork->AddGate(sxdaggate,
static_cast<unsigned int>(qubit));
321 pp->ApplySXDG(
static_cast<unsigned int>(qubit));
323 QC::Gates::AppliedGate<> agate(sxdaggate.getRawOperatorMatrix(), qubit);
324 pathIntegralSimulator->ApplyGate(agate);
327 state->ApplyGate(sxdaggate,
static_cast<unsigned int>(qubit));
328 NotifyObservers({qubit});
339 mpsSimulator->ApplyGate(k,
static_cast<unsigned int>(qubit));
341 cliffordSimulator->ApplyK(
static_cast<unsigned int>(qubit));
343 tensorNetwork->AddGate(k,
static_cast<unsigned int>(qubit));
345 pp->ApplyK(
static_cast<unsigned int>(qubit));
347 QC::Gates::AppliedGate<> agate(k.getRawOperatorMatrix(), qubit);
348 pathIntegralSimulator->ApplyGate(agate);
351 state->ApplyGate(k,
static_cast<unsigned int>(qubit));
352 NotifyObservers({qubit});
363 rxgate.SetTheta(theta);
365 mpsSimulator->ApplyGate(rxgate,
static_cast<unsigned int>(qubit));
367 throw std::runtime_error(
368 "QCSimSimulator::ApplyRx: The stabilizer "
369 "simulator does not support the Rx gate.");
371 tensorNetwork->AddGate(rxgate,
static_cast<unsigned int>(qubit));
373 pp->ApplyRX(
static_cast<unsigned int>(qubit), theta);
375 QC::Gates::AppliedGate<> agate(rxgate.getRawOperatorMatrix(), qubit);
376 pathIntegralSimulator->ApplyGate(agate);
379 state->ApplyGate(rxgate,
static_cast<unsigned int>(qubit));
380 NotifyObservers({qubit});
391 rygate.SetTheta(theta);
393 mpsSimulator->ApplyGate(rygate,
static_cast<unsigned int>(qubit));
395 throw std::runtime_error(
396 "QCSimSimulator::ApplyRy: The stabilizer "
397 "simulator does not support the Ry gate.");
399 tensorNetwork->AddGate(rygate,
static_cast<unsigned int>(qubit));
401 pp->ApplyRY(
static_cast<unsigned int>(qubit), theta);
403 QC::Gates::AppliedGate<> agate(rygate.getRawOperatorMatrix(), qubit);
404 pathIntegralSimulator->ApplyGate(agate);
407 state->ApplyGate(rygate,
static_cast<unsigned int>(qubit));
408 NotifyObservers({qubit});
419 rzgate.SetTheta(theta);
421 mpsSimulator->ApplyGate(rzgate,
static_cast<unsigned int>(qubit));
423 throw std::runtime_error(
424 "QCSimSimulator::ApplyRz: The stabilizer "
425 "simulator does not support the Rz gate.");
427 tensorNetwork->AddGate(rzgate,
static_cast<unsigned int>(qubit));
429 pp->ApplyRZ(
static_cast<unsigned int>(qubit), theta);
431 QC::Gates::AppliedGate<> agate(rzgate.getRawOperatorMatrix(), qubit);
432 pathIntegralSimulator->ApplyGate(agate);
435 state->ApplyGate(rzgate,
static_cast<unsigned int>(qubit));
436 NotifyObservers({qubit});
450 double gamma)
override {
451 ugate.SetParams(theta, phi, lambda, gamma);
453 mpsSimulator->ApplyGate(ugate,
static_cast<unsigned int>(qubit));
455 throw std::runtime_error(
456 "QCSimSimulator::ApplyU: The stabilizer "
457 "simulator does not support the U gate.");
459 tensorNetwork->AddGate(ugate,
static_cast<unsigned int>(qubit));
461 pp->ApplyU(
static_cast<unsigned int>(qubit), theta, phi, lambda, gamma);
463 QC::Gates::AppliedGate<> agate(ugate.getRawOperatorMatrix(), qubit);
464 pathIntegralSimulator->ApplyGate(agate);
467 state->ApplyGate(ugate,
static_cast<unsigned int>(qubit));
468 NotifyObservers({qubit});
480 mpsSimulator->ApplyGate(cxgate,
static_cast<unsigned int>(tgt_qubit),
481 static_cast<unsigned int>(ctrl_qubit));
483 cliffordSimulator->ApplyCX(
static_cast<unsigned int>(tgt_qubit),
484 static_cast<unsigned int>(ctrl_qubit));
486 tensorNetwork->AddGate(cxgate,
static_cast<unsigned int>(ctrl_qubit),
487 static_cast<unsigned int>(tgt_qubit));
489 pp->ApplyCX(
static_cast<unsigned int>(ctrl_qubit),
490 static_cast<unsigned int>(tgt_qubit));
492 QC::Gates::AppliedGate<> agate(cxgate.getRawOperatorMatrix(),
493 tgt_qubit, ctrl_qubit);
494 pathIntegralSimulator->ApplyGate(agate);
497 state->ApplyGate(cxgate,
static_cast<unsigned int>(tgt_qubit),
498 static_cast<unsigned int>(ctrl_qubit));
499 NotifyObservers({tgt_qubit, ctrl_qubit});
511 mpsSimulator->ApplyGate(cygate,
static_cast<unsigned int>(tgt_qubit),
512 static_cast<unsigned int>(ctrl_qubit));
514 cliffordSimulator->ApplyCY(
static_cast<unsigned int>(tgt_qubit),
515 static_cast<unsigned int>(ctrl_qubit));
517 tensorNetwork->AddGate(cygate,
static_cast<unsigned int>(ctrl_qubit),
518 static_cast<unsigned int>(tgt_qubit));
520 pp->ApplyCY(
static_cast<unsigned int>(ctrl_qubit),
521 static_cast<unsigned int>(tgt_qubit));
523 QC::Gates::AppliedGate<> agate(cygate.getRawOperatorMatrix(),
524 tgt_qubit, ctrl_qubit);
525 pathIntegralSimulator->ApplyGate(agate);
528 state->ApplyGate(cygate,
static_cast<unsigned int>(tgt_qubit),
529 static_cast<unsigned int>(ctrl_qubit));
530 NotifyObservers({tgt_qubit, ctrl_qubit});
542 mpsSimulator->ApplyGate(czgate,
static_cast<unsigned int>(tgt_qubit),
543 static_cast<unsigned int>(ctrl_qubit));
545 cliffordSimulator->ApplyCZ(
static_cast<unsigned int>(tgt_qubit),
546 static_cast<unsigned int>(ctrl_qubit));
548 tensorNetwork->AddGate(czgate,
static_cast<unsigned int>(ctrl_qubit),
549 static_cast<unsigned int>(tgt_qubit));
551 pp->ApplyCZ(
static_cast<unsigned int>(ctrl_qubit),
552 static_cast<unsigned int>(tgt_qubit));
554 QC::Gates::AppliedGate<> agate(czgate.getRawOperatorMatrix(),
555 tgt_qubit, ctrl_qubit);
556 pathIntegralSimulator->ApplyGate(agate);
559 state->ApplyGate(czgate,
static_cast<unsigned int>(tgt_qubit),
560 static_cast<unsigned int>(ctrl_qubit));
561 NotifyObservers({tgt_qubit, ctrl_qubit});
573 double lambda)
override {
574 cpgate.SetPhaseShift(lambda);
576 mpsSimulator->ApplyGate(cpgate,
static_cast<unsigned int>(tgt_qubit),
577 static_cast<unsigned int>(ctrl_qubit));
579 throw std::runtime_error(
580 "QCSimSimulator::ApplyCP: The stabilizer "
581 "simulator does not support the CP gate.");
583 tensorNetwork->AddGate(cpgate,
static_cast<unsigned int>(ctrl_qubit),
584 static_cast<unsigned int>(tgt_qubit));
586 pp->ApplyCP(
static_cast<unsigned int>(ctrl_qubit),
587 static_cast<unsigned int>(tgt_qubit), lambda);
589 QC::Gates::AppliedGate<> agate(cpgate.getRawOperatorMatrix(),
590 tgt_qubit, ctrl_qubit);
591 pathIntegralSimulator->ApplyGate(agate);
594 state->ApplyGate(cpgate,
static_cast<unsigned int>(tgt_qubit),
595 static_cast<unsigned int>(ctrl_qubit));
596 NotifyObservers({tgt_qubit, ctrl_qubit});
608 double theta)
override {
609 crxgate.SetTheta(theta);
611 mpsSimulator->ApplyGate(crxgate,
static_cast<unsigned int>(tgt_qubit),
612 static_cast<unsigned int>(ctrl_qubit));
614 throw std::runtime_error(
615 "QCSimSimulator::ApplyCRx: The stabilizer "
616 "simulator does not support the CRx gate.");
618 tensorNetwork->AddGate(crxgate,
static_cast<unsigned int>(ctrl_qubit),
619 static_cast<unsigned int>(tgt_qubit));
621 pp->ApplyCRX(
static_cast<unsigned int>(ctrl_qubit),
622 static_cast<unsigned int>(tgt_qubit), theta);
624 QC::Gates::AppliedGate<> agate(crxgate.getRawOperatorMatrix(),
625 tgt_qubit, ctrl_qubit);
626 pathIntegralSimulator->ApplyGate(agate);
629 state->ApplyGate(crxgate,
static_cast<unsigned int>(tgt_qubit),
630 static_cast<unsigned int>(ctrl_qubit));
631 NotifyObservers({tgt_qubit, ctrl_qubit});
643 double theta)
override {
644 crygate.SetTheta(theta);
646 mpsSimulator->ApplyGate(crygate,
static_cast<unsigned int>(tgt_qubit),
647 static_cast<unsigned int>(ctrl_qubit));
649 throw std::runtime_error(
650 "QCSimSimulator::ApplyCRy: The stabilizer "
651 "simulator does not support the CRy gate.");
653 tensorNetwork->AddGate(crygate,
static_cast<unsigned int>(ctrl_qubit),
654 static_cast<unsigned int>(tgt_qubit));
656 pp->ApplyCRY(
static_cast<unsigned int>(ctrl_qubit),
657 static_cast<unsigned int>(tgt_qubit), theta);
659 QC::Gates::AppliedGate<> agate(crygate.getRawOperatorMatrix(),
660 tgt_qubit, ctrl_qubit);
661 pathIntegralSimulator->ApplyGate(agate);
664 state->ApplyGate(crygate,
static_cast<unsigned int>(tgt_qubit),
665 static_cast<unsigned int>(ctrl_qubit));
666 NotifyObservers({tgt_qubit, ctrl_qubit});
678 double theta)
override {
679 crzgate.SetTheta(theta);
681 mpsSimulator->ApplyGate(crzgate,
static_cast<unsigned int>(tgt_qubit),
682 static_cast<unsigned int>(ctrl_qubit));
684 throw std::runtime_error(
685 "QCSimSimulator::ApplyCRz: The stabilizer "
686 "simulator does not support the CRz gate.");
688 tensorNetwork->AddGate(crzgate,
static_cast<unsigned int>(ctrl_qubit),
689 static_cast<unsigned int>(tgt_qubit));
691 pp->ApplyCRZ(
static_cast<unsigned int>(ctrl_qubit),
692 static_cast<unsigned int>(tgt_qubit), theta);
694 QC::Gates::AppliedGate<> agate(crzgate.getRawOperatorMatrix(), tgt_qubit,
696 pathIntegralSimulator->ApplyGate(agate);
699 state->ApplyGate(crzgate,
static_cast<unsigned int>(tgt_qubit),
700 static_cast<unsigned int>(ctrl_qubit));
701 NotifyObservers({tgt_qubit, ctrl_qubit});
713 mpsSimulator->ApplyGate(ch,
static_cast<unsigned int>(tgt_qubit),
714 static_cast<unsigned int>(ctrl_qubit));
716 throw std::runtime_error(
717 "QCSimSimulator::ApplyCH: The stabilizer "
718 "simulator does not support the CH gate.");
720 tensorNetwork->AddGate(ch,
static_cast<unsigned int>(ctrl_qubit),
721 static_cast<unsigned int>(tgt_qubit));
723 pp->ApplyCH(
static_cast<unsigned int>(ctrl_qubit),
724 static_cast<unsigned int>(tgt_qubit));
726 QC::Gates::AppliedGate<> agate(ch.getRawOperatorMatrix(), tgt_qubit,
728 pathIntegralSimulator->ApplyGate(agate);
731 state->ApplyGate(ch,
static_cast<unsigned int>(tgt_qubit),
732 static_cast<unsigned int>(ctrl_qubit));
733 NotifyObservers({tgt_qubit, ctrl_qubit});
745 mpsSimulator->ApplyGate(csx,
static_cast<unsigned int>(tgt_qubit),
746 static_cast<unsigned int>(ctrl_qubit));
748 throw std::runtime_error(
749 "QCSimSimulator::ApplyCSx: The stabilizer "
750 "simulator does not support the CSx gate.");
752 tensorNetwork->AddGate(csx,
static_cast<unsigned int>(ctrl_qubit),
753 static_cast<unsigned int>(tgt_qubit));
755 pp->ApplyCSX(
static_cast<unsigned int>(ctrl_qubit),
756 static_cast<unsigned int>(tgt_qubit));
758 QC::Gates::AppliedGate<> agate(csx.getRawOperatorMatrix(), tgt_qubit,
760 pathIntegralSimulator->ApplyGate(agate);
763 state->ApplyGate(csx,
static_cast<unsigned int>(tgt_qubit),
764 static_cast<unsigned int>(ctrl_qubit));
765 NotifyObservers({tgt_qubit, ctrl_qubit});
778 mpsSimulator->ApplyGate(csxdag,
static_cast<unsigned int>(tgt_qubit),
779 static_cast<unsigned int>(ctrl_qubit));
781 throw std::runtime_error(
782 "QCSimSimulator::ApplyCSxDAG: The stabilizer "
783 "simulator does not support the CSxDag gate.");
785 tensorNetwork->AddGate(csxdag,
static_cast<unsigned int>(ctrl_qubit),
786 static_cast<unsigned int>(tgt_qubit));
788 pp->ApplyCSXDAG(
static_cast<unsigned int>(ctrl_qubit),
789 static_cast<unsigned int>(tgt_qubit));
791 QC::Gates::AppliedGate<> agate(csxdag.getRawOperatorMatrix(), tgt_qubit,
793 pathIntegralSimulator->ApplyGate(agate);
796 state->ApplyGate(csxdag,
static_cast<unsigned int>(tgt_qubit),
797 static_cast<unsigned int>(ctrl_qubit));
798 NotifyObservers({tgt_qubit, ctrl_qubit});
810 mpsSimulator->ApplyGate(swapgate,
static_cast<unsigned int>(qubit1),
811 static_cast<unsigned int>(qubit0));
813 cliffordSimulator->ApplySwap(
static_cast<unsigned int>(qubit1),
814 static_cast<unsigned int>(qubit0));
816 tensorNetwork->AddGate(swapgate,
static_cast<unsigned int>(qubit0),
817 static_cast<unsigned int>(qubit1));
819 pp->ApplySWAP(
static_cast<unsigned int>(qubit0),
820 static_cast<unsigned int>(qubit1));
822 QC::Gates::AppliedGate<> agate(swapgate.getRawOperatorMatrix(), qubit1,
824 pathIntegralSimulator->ApplyGate(agate);
827 state->ApplyGate(swapgate,
static_cast<unsigned int>(qubit1),
828 static_cast<unsigned int>(qubit0));
829 NotifyObservers({qubit1, qubit0});
843 const size_t q1 = qubit0;
844 const size_t q2 = qubit1;
845 const size_t q3 = qubit2;
848 mpsSimulator->ApplyGate(csx,
static_cast<unsigned int>(q3),
849 static_cast<unsigned int>(q2));
850 NotifyObservers({qubit1, qubit2});
852 mpsSimulator->ApplyGate(cxgate,
static_cast<unsigned int>(q2),
853 static_cast<unsigned int>(q1));
854 NotifyObservers({qubit0, qubit1});
856 mpsSimulator->ApplyGate(csxdag,
static_cast<unsigned int>(q3),
857 static_cast<unsigned int>(q2));
858 NotifyObservers({qubit1, qubit2});
860 mpsSimulator->ApplyGate(cxgate,
static_cast<unsigned int>(q2),
861 static_cast<unsigned int>(q1));
862 NotifyObservers({qubit0, qubit1});
864 mpsSimulator->ApplyGate(csx,
static_cast<unsigned int>(q3),
865 static_cast<unsigned int>(q1));
866 NotifyObservers({qubit0, qubit2});
868 throw std::runtime_error(
869 "QCSimSimulator::ApplyCCX: The stabilizer "
870 "simulator does not support the CCX gate.");
872 const size_t q1 = qubit0;
873 const size_t q2 = qubit1;
874 const size_t q3 = qubit2;
877 tensorNetwork->AddGate(csx,
static_cast<unsigned int>(q2),
878 static_cast<unsigned int>(q3));
879 NotifyObservers({qubit1, qubit2});
881 tensorNetwork->AddGate(cxgate,
static_cast<unsigned int>(q1),
882 static_cast<unsigned int>(q2));
883 NotifyObservers({qubit0, qubit1});
885 tensorNetwork->AddGate(csxdag,
static_cast<unsigned int>(q2),
886 static_cast<unsigned int>(q3));
887 NotifyObservers({qubit1, qubit2});
889 tensorNetwork->AddGate(cxgate,
static_cast<unsigned int>(q1),
890 static_cast<unsigned int>(q2));
891 NotifyObservers({qubit0, qubit1});
893 tensorNetwork->AddGate(csx,
static_cast<unsigned int>(q1),
894 static_cast<unsigned int>(q3));
895 NotifyObservers({qubit0, qubit2});
897 pp->ApplyCCX(
static_cast<unsigned int>(qubit0),
898 static_cast<unsigned int>(qubit1),
899 static_cast<unsigned int>(qubit2));
900 NotifyObservers({qubit2, qubit1, qubit0});
902 QC::Gates::AppliedGate<> agate(ccxgate.getRawOperatorMatrix(), qubit2,
904 pathIntegralSimulator->ApplyGate(agate);
905 NotifyObservers({qubit2, qubit1, qubit0});
907 state->ApplyGate(ccxgate,
static_cast<unsigned int>(qubit2),
908 static_cast<unsigned int>(qubit1),
909 static_cast<unsigned int>(qubit0));
910 NotifyObservers({qubit2, qubit1, qubit0});
925 const size_t q1 = ctrl_qubit;
926 const size_t q2 = qubit0;
927 const size_t q3 = qubit1;
931 mpsSimulator->ApplyGate(cxgate,
static_cast<unsigned int>(q2),
932 static_cast<unsigned int>(q3));
933 NotifyObservers({qubit1, qubit0});
935 mpsSimulator->ApplyGate(csx,
static_cast<unsigned int>(q3),
936 static_cast<unsigned int>(q2));
937 NotifyObservers({qubit0, qubit1});
939 mpsSimulator->ApplyGate(cxgate,
static_cast<unsigned int>(q2),
940 static_cast<unsigned int>(q1));
941 NotifyObservers({ctrl_qubit, qubit0});
943 pgate.SetPhaseShift(M_PI);
944 mpsSimulator->ApplyGate(pgate,
static_cast<unsigned int>(q3));
945 NotifyObservers({qubit1});
946 pgate.SetPhaseShift(-M_PI_2);
947 mpsSimulator->ApplyGate(pgate,
static_cast<unsigned int>(q2));
948 NotifyObservers({qubit0});
950 mpsSimulator->ApplyGate(csx,
static_cast<unsigned int>(q3),
951 static_cast<unsigned int>(q2));
952 NotifyObservers({qubit0, qubit1});
954 mpsSimulator->ApplyGate(cxgate,
static_cast<unsigned int>(q2),
955 static_cast<unsigned int>(q1));
956 NotifyObservers({ctrl_qubit, qubit0});
958 pgate.SetPhaseShift(M_PI);
959 mpsSimulator->ApplyGate(pgate,
static_cast<unsigned int>(q3));
960 NotifyObservers({qubit1});
962 mpsSimulator->ApplyGate(csx,
static_cast<unsigned int>(q3),
963 static_cast<unsigned int>(q1));
964 NotifyObservers({ctrl_qubit, qubit1});
966 mpsSimulator->ApplyGate(cxgate,
static_cast<unsigned int>(q2),
967 static_cast<unsigned int>(q3));
968 NotifyObservers({qubit1, qubit0});
970 throw std::runtime_error(
971 "QCSimSimulator::ApplyCSwap: The stabilizer "
972 "simulator does not support the CSwap gate.");
974 const size_t q1 = ctrl_qubit;
975 const size_t q2 = qubit0;
976 const size_t q3 = qubit1;
980 tensorNetwork->AddGate(cxgate,
static_cast<unsigned int>(q3),
981 static_cast<unsigned int>(q2));
982 NotifyObservers({qubit1, qubit0});
984 tensorNetwork->AddGate(csx,
static_cast<unsigned int>(q2),
985 static_cast<unsigned int>(q3));
986 NotifyObservers({qubit0, qubit1});
988 tensorNetwork->AddGate(cxgate,
static_cast<unsigned int>(q1),
989 static_cast<unsigned int>(q2));
990 NotifyObservers({ctrl_qubit, qubit0});
992 pgate.SetPhaseShift(M_PI);
993 tensorNetwork->AddGate(pgate,
static_cast<unsigned int>(q3));
994 NotifyObservers({qubit1});
995 pgate.SetPhaseShift(-M_PI_2);
996 tensorNetwork->AddGate(pgate,
static_cast<unsigned int>(q2));
997 NotifyObservers({qubit0});
999 tensorNetwork->AddGate(csx,
static_cast<unsigned int>(q2),
1000 static_cast<unsigned int>(q3));
1001 NotifyObservers({qubit0, qubit1});
1003 tensorNetwork->AddGate(cxgate,
static_cast<unsigned int>(q1),
1004 static_cast<unsigned int>(q2));
1005 NotifyObservers({ctrl_qubit, qubit0});
1007 pgate.SetPhaseShift(M_PI);
1008 tensorNetwork->AddGate(pgate,
static_cast<unsigned int>(q3));
1009 NotifyObservers({qubit1});
1011 tensorNetwork->AddGate(csx,
static_cast<unsigned int>(q1),
1012 static_cast<unsigned int>(q3));
1013 NotifyObservers({ctrl_qubit, qubit1});
1015 tensorNetwork->AddGate(cxgate,
static_cast<unsigned int>(q3),
1016 static_cast<unsigned int>(q2));
1017 NotifyObservers({qubit1, qubit0});
1019 pp->ApplyCSwap(
static_cast<unsigned int>(ctrl_qubit),
1020 static_cast<unsigned int>(qubit0),
1021 static_cast<unsigned int>(qubit1));
1022 NotifyObservers({qubit1, qubit0, ctrl_qubit});
1024 QC::Gates::AppliedGate<> agate(cswapgate.getRawOperatorMatrix(),
1025 qubit1, qubit0, ctrl_qubit);
1026 pathIntegralSimulator->ApplyGate(agate);
1027 NotifyObservers({qubit1, qubit0, ctrl_qubit});
1029 state->ApplyGate(cswapgate,
static_cast<unsigned int>(qubit1),
1030 static_cast<unsigned int>(qubit0),
1031 static_cast<unsigned int>(ctrl_qubit));
1032 NotifyObservers({qubit1, qubit0, ctrl_qubit});
1048 double theta,
double phi,
double lambda,
double gamma)
override {
1049 cugate.SetParams(theta, phi, lambda, gamma);
1051 mpsSimulator->ApplyGate(cugate,
static_cast<unsigned int>(tgt_qubit),
1052 static_cast<unsigned int>(ctrl_qubit));
1054 throw std::runtime_error(
1055 "QCSimSimulator::ApplyCU: The stabilizer "
1056 "simulator does not support the CU gate.");
1058 tensorNetwork->AddGate(cugate,
static_cast<unsigned int>(ctrl_qubit),
1059 static_cast<unsigned int>(tgt_qubit));
1061 pp->ApplyCU(
static_cast<unsigned int>(ctrl_qubit),
1062 static_cast<unsigned int>(tgt_qubit), theta, phi, lambda,
1065 QC::Gates::AppliedGate<> agate(cugate.getRawOperatorMatrix(), tgt_qubit,
1067 pathIntegralSimulator->ApplyGate(agate);
1070 state->ApplyGate(cugate,
static_cast<unsigned int>(tgt_qubit),
1071 static_cast<unsigned int>(ctrl_qubit));
1072 NotifyObservers({tgt_qubit, ctrl_qubit});
1082 void ApplyNop()
override {
1096 std::unique_ptr<ISimulator> Clone()
override {
1097 auto cloned = std::make_unique<QCSimSimulator>();
1099 cloned->simulationType = simulationType;
1100 cloned->nrQubits = nrQubits;
1102 cloned->limitSize = limitSize;
1103 cloned->limitEntanglement = limitEntanglement;
1105 cloned->singularValueThreshold = singularValueThreshold;
1107 cloned->enableMultithreading = enableMultithreading;
1108 cloned->useMPSMeasureNoCollapse = useMPSMeasureNoCollapse;
1110 cloned->lookaheadDepth = lookaheadDepth;
1111 cloned->useOptimalMeetingPosition = useOptimalMeetingPosition;
1112 cloned->upcomingGates = upcomingGates;
1113 cloned->upcomingGateIndex = upcomingGateIndex;
1114 cloned->growthFactorGate = growthFactorGate;
1115 cloned->growthFactorSwap = growthFactorSwap;
1117 if (state) cloned->state = state->Clone();
1120 cloned->mpsSimulator = mpsSimulator->Clone();
1122 if (limitEntanglement && singularValueThreshold > 0.)
1123 cloned->mpsSimulator->setLimitEntanglement(singularValueThreshold);
1124 if (limitSize && chi > 0)
1125 cloned->mpsSimulator->setLimitBondDimension(chi);
1127 cloned->dummySim = dummySim ? dummySim->Clone() :
nullptr;
1129 cloned->gateCounterObserver =
1130 std::make_shared<GateCounterObserver>(upcomingGateIndex);
1131 cloned->RegisterObserver(cloned->gateCounterObserver);
1134 if (cliffordSimulator)
1135 cloned->cliffordSimulator = cliffordSimulator->Clone();
1137 if (tensorNetwork) cloned->tensorNetwork = tensorNetwork->Clone();
1139 if (pp) cloned->pp = pp->Clone();
1141 if (pathIntegralSimulator)
1142 cloned->pathIntegralSimulator = pathIntegralSimulator->Clone();
1148 QC::Gates::PhaseShiftGate<> pgate;
1149 QC::Gates::PauliXGate<> xgate;
1150 QC::Gates::PauliYGate<> ygate;
1151 QC::Gates::PauliZGate<> zgate;
1152 QC::Gates::HadamardGate<> h;
1154 QC::Gates::SGate<> sgate;
1155 QC::Gates::SDGGate<> sdggate;
1156 QC::Gates::TGate<> tgate;
1157 QC::Gates::TDGGate<> tdggate;
1158 QC::Gates::SquareRootNOTGate<> sxgate;
1159 QC::Gates::SquareRootNOTDagGate<> sxdaggate;
1160 QC::Gates::HyGate<> k;
1161 QC::Gates::RxGate<> rxgate;
1162 QC::Gates::RyGate<> rygate;
1163 QC::Gates::RzGate<> rzgate;
1164 QC::Gates::UGate<> ugate;
1165 QC::Gates::CNOTGate<> cxgate;
1166 QC::Gates::ControlledYGate<> cygate;
1167 QC::Gates::ControlledZGate<> czgate;
1168 QC::Gates::ControlledPhaseShiftGate<> cpgate;
1169 QC::Gates::ControlledRxGate<> crxgate;
1170 QC::Gates::ControlledRyGate<> crygate;
1171 QC::Gates::ControlledRzGate<> crzgate;
1172 QC::Gates::ControlledHadamardGate<> ch;
1173 QC::Gates::ControlledSquareRootNOTGate<> csx;
1174 QC::Gates::ControlledSquareRootNOTDagGate<> csxdag;
1175 QC::Gates::SwapGate<> swapgate;
1176 QC::Gates::ToffoliGate<> ccxgate;
1177 QC::Gates::FredkinGate<> cswapgate;
1178 QC::Gates::ControlledUGate<> cugate;
int ApplyK(void *sim, int qubit)
int ApplyRx(void *sim, int qubit, double theta)
int ApplyX(void *sim, int qubit)
int ApplyU(void *sim, int qubit, double theta, double phi, double lambda, double gamma)
int ApplyCRy(void *sim, int controlQubit, int targetQubit, double theta)
int ApplyTDG(void *sim, int qubit)
int ApplyS(void *sim, int qubit)
int ApplyCX(void *sim, int controlQubit, int targetQubit)
int ApplyCRz(void *sim, int controlQubit, int targetQubit, double theta)
int ApplyCP(void *sim, int controlQubit, int targetQubit, double theta)
int ApplySDG(void *sim, int qubit)
int ApplyCSwap(void *sim, int controlQubit, int qubit1, int qubit2)
int ApplyCCX(void *sim, int controlQubit1, int controlQubit2, int targetQubit)
int ApplyY(void *sim, int qubit)
int ApplyZ(void *sim, int qubit)
int ApplyH(void *sim, int qubit)
int ApplyCY(void *sim, int controlQubit, int targetQubit)
int ApplyCU(void *sim, int controlQubit, int targetQubit, double theta, double phi, double lambda, double gamma)
int ApplySwap(void *sim, int qubit1, int qubit2)
int ApplyRy(void *sim, int qubit, double theta)
int ApplyP(void *sim, int qubit, double theta)
int ApplyCH(void *sim, int controlQubit, int targetQubit)
int GetSimulationType(void *sim)
int ApplyCZ(void *sim, int controlQubit, int targetQubit)
int ApplyRz(void *sim, int qubit, double theta)
int ApplyT(void *sim, int qubit)
int ApplyCRx(void *sim, int controlQubit, int targetQubit, double theta)
uint_fast64_t qubit_t
The type of a qubit.