15#ifndef _GPU_LIB_MPS_SIM_H_
16#define _GPU_LIB_MPS_SIM_H_
29 explicit GpuLibMPSSim(
const std::shared_ptr<GpuLibrary>& lib,
int device = -1)
30 : lib(lib), obj(
nullptr) {
32 auto lock = lib->LockInitialization();
33 if (lib->SetGpuDevice(device == -1 ? lib->GetCreationDevice() : device))
34 obj = lib->CreateMPS();
38 int GetGpuDevice()
const {
return lib ? lib->MPSGetGpuId(obj) : -1; }
40 GpuLibMPSSim(
const std::shared_ptr<GpuLibrary> &lib,
void *obj)
41 : lib(lib), obj(obj) {}
43 GpuLibMPSSim() =
delete;
44 GpuLibMPSSim(
const GpuLibMPSSim &) =
delete;
45 GpuLibMPSSim &operator=(
const GpuLibMPSSim &) =
delete;
46 GpuLibMPSSim(GpuLibMPSSim &&) =
default;
47 GpuLibMPSSim &operator=(GpuLibMPSSim &&) =
default;
50 if (lib && obj) lib->DestroyMPS(obj);
53 bool Create(
unsigned int nrQubits) {
54 if (obj)
return lib->MPSCreate(obj, nrQubits);
59 bool CreateWithBasisState(
unsigned int nrQubits,
unsigned long long state) {
60 if (obj)
return lib->MPSCreateWithBasisState(obj, nrQubits, state);
65 bool CreateWithBasisStateBits(
unsigned int nrQubits,
66 const std::vector<unsigned char> &stateBits) {
68 return lib->MPSCreateWithBasisStateBits(obj, nrQubits,
75 if (obj)
return lib->MPSReset(obj);
80 bool SetSeed(uint64_t seed) {
return obj && lib->MPSSetSeed(obj, seed); }
82 bool SetInitialQubitsMap(
const std::vector<long long int> &initialMap) {
83 if (obj)
return lib->MPSSetInitialQubitsMap(obj, initialMap);
88 bool SetUseOptimalMeetingPosition(
bool useOptimalMeetingPosition) {
89 if (obj)
return lib->MPSSetUseOptimalMeetingPosition(obj, useOptimalMeetingPosition);
93 bool GetUseOptimalMeetingPosition()
const {
94 if (obj)
return lib->MPSGetUseOptimalMeetingPosition(obj);
98 bool IsValid()
const {
99 if (obj)
return lib->MPSIsValid(obj);
104 bool IsCreated()
const {
105 if (obj)
return lib->MPSIsCreated(obj);
110 bool SetDataType(
int useDoublePrecision) {
111 if (obj)
return lib->MPSSetDataType(obj, useDoublePrecision);
116 bool IsDoublePrecision()
const {
117 if (obj)
return lib->MPSIsDoublePrecision(obj);
122 bool SetCutoff(
double val) {
123 if (obj)
return lib->MPSSetCutoff(obj, val);
128 double GetCutoff()
const {
129 if (obj)
return lib->MPSGetCutoff(obj);
136 bool SetTruncationMode(
int mode) {
137 if (obj)
return lib->MPSSetTruncationMode(obj, mode);
142 int GetTruncationMode()
const {
143 if (obj)
return lib->MPSGetTruncationMode(obj);
148 bool SetGesvdJ(
int val) {
149 if (obj)
return lib->MPSSetGesvdJ(obj, val);
154 bool GetGesvdJ()
const {
155 if (obj)
return lib->MPSGetGesvdJ(obj);
161 bool SetGesvdP(
bool enable) {
162 return obj && lib->MPSSetGesvdP(obj, enable);
164 bool GetGesvdP()
const {
return lib->MPSGetGesvdP(obj); }
165 bool SetGesvdR(
bool enable) {
166 return obj && lib->MPSSetGesvdR(obj, enable);
168 bool GetGesvdR()
const {
return lib->MPSGetGesvdR(obj); }
169 int GetLastSvdAlgo()
const {
return lib->MPSGetLastSvdAlgo(obj); }
171 bool SetMaxExtent(
long int val) {
172 if (obj)
return lib->MPSSetMaxExtent(obj, val);
177 long int GetMaxExtent()
const {
178 if (obj)
return lib->MPSGetMaxExtent(obj);
183 int GetNrQubits()
const {
184 if (obj)
return lib->MPSGetNrQubits(obj);
189 std::vector<long long int> GetBondDimensions(
size_t nrQubits)
const {
190 if (!obj || nrQubits < 2)
return {};
191 std::vector<long long int> bondDims(nrQubits - 1);
192 if (!lib->MPSGetBondDimensions(obj, bondDims.data()))
return {};
196 bool SetCallbackContext(
void *context) {
197 if (obj)
return lib->MPSSetCallbackContext(obj, context);
201 bool SetMeetingPositionCallback(int64_t (*callback)(
void *,
const int64_t *)) {
202 if (obj)
return lib->MPSSetMeetingPositionCallback(obj, callback);
206 bool SetBondDimensionsCallback(
void (*callback)(
void*,
const int64_t*)) {
207 if (obj)
return lib->MPSSetBondDimensionsCallback(obj, callback);
211 bool Amplitude(
long int numFixedValues,
long int *fixedValues,
double *real,
212 double *imaginary)
const {
214 return lib->MPSAmplitude(obj, numFixedValues, fixedValues, real,
220 double Probability0(
unsigned int qubit)
const {
221 if (obj)
return lib->MPSProbability0(obj, qubit);
226 bool Measure(
unsigned int qubit) {
227 if (obj)
return lib->MPSMeasure(obj, qubit);
232 bool MeasureQubits(
long int numQubits,
unsigned int *qubits,
int *result) {
233 if (obj)
return lib->MPSMeasureQubits(obj, numQubits, qubits, result);
238 std::unordered_map<std::vector<bool>, int64_t> *GetMapForSample()
const {
239 if (lib)
return lib->MPSGetMapForSample();
244 bool FreeMapForSample(
245 std::unordered_map<std::vector<bool>, int64_t> *map)
const {
246 if (lib)
return lib->MPSFreeMapForSample(map);
251 bool Sample(
long int numShots,
long int numQubits,
unsigned int *qubits,
253 if (obj)
return lib->MPSSample(obj, numShots, numQubits, qubits, resultMap);
258 bool SampleRaw(
unsigned int nSamples,
long int *samples,
unsigned int nBits,
259 const unsigned int *bitOrdering) {
261 return lib->MPSSampleRaw(obj, nSamples, samples, nBits, bitOrdering);
266 bool SampleAll(
unsigned int nSamples,
long int *samples) {
267 if (obj)
return lib->MPSSampleAll(obj, nSamples, samples);
273 if (obj)
return lib->MPSSaveState(obj);
279 if (obj)
return lib->MPSRestoreState(obj);
284 bool CleanSavedState() {
285 if (obj)
return lib->MPSCleanSavedState(obj);
290 std::unique_ptr<GpuLibMPSSim> Clone()
const {
291 if (obj)
return std::make_unique<GpuLibMPSSim>(lib, lib->MPSClone(obj));
296 double ExpectationValue(
const std::string &pauliString) {
298 return lib->MPSExpectationValue(obj, pauliString.c_str(),
299 pauliString.length());
304 std::complex<double> ProjectOnZero() {
305 if (obj)
return lib->MPSProjectOnZero(obj);
307 return std::complex<double>(0., 0.);
310 bool ApplyX(
unsigned int siteA) {
311 if (obj)
return lib->MPSApplyX(obj, siteA);
316 bool ApplyY(
unsigned int siteA) {
317 if (obj)
return lib->MPSApplyY(obj, siteA);
322 bool ApplyZ(
unsigned int siteA) {
323 if (obj)
return lib->MPSApplyZ(obj, siteA);
328 bool ApplyH(
unsigned int siteA) {
329 if (obj)
return lib->MPSApplyH(obj, siteA);
334 bool ApplyS(
unsigned int siteA) {
335 if (obj)
return lib->MPSApplyS(obj, siteA);
341 if (obj)
return lib->MPSApplySDG(obj, siteA);
346 bool ApplyT(
unsigned int siteA) {
347 if (obj)
return lib->MPSApplyT(obj, siteA);
353 if (obj)
return lib->MPSApplyTDG(obj, siteA);
358 bool ApplySX(
unsigned int siteA) {
359 if (obj)
return lib->MPSApplySX(obj, siteA);
365 if (obj)
return lib->MPSApplySXDG(obj, siteA);
370 bool ApplyK(
unsigned int siteA) {
371 if (obj)
return lib->MPSApplyK(obj, siteA);
376 bool ApplyP(
unsigned int siteA,
double theta) {
377 if (obj)
return lib->MPSApplyP(obj, siteA, theta);
382 bool ApplyRx(
unsigned int siteA,
double theta) {
383 if (obj)
return lib->MPSApplyRx(obj, siteA, theta);
388 bool ApplyRy(
unsigned int siteA,
double theta) {
389 if (obj)
return lib->MPSApplyRy(obj, siteA, theta);
394 bool ApplyRz(
unsigned int siteA,
double theta) {
395 if (obj)
return lib->MPSApplyRz(obj, siteA, theta);
400 bool ApplyU(
unsigned int siteA,
double theta,
double phi,
double lambda,
402 if (obj)
return lib->MPSApplyU(obj, siteA, theta, phi, lambda, gamma);
407 bool ApplyOneQubitMatrix(
unsigned int qubit,
408 const double *matrixInterleaved) {
409 if (obj)
return lib->MPSApplyOneQubitMatrix(obj, qubit, matrixInterleaved);
414 bool ApplyTwoQubitMatrix(
unsigned int qubit1,
unsigned int qubit2,
415 const double *matrixInterleaved) {
417 return lib->MPSApplyTwoQubitMatrix(obj, qubit1, qubit2,
423 bool ApplySwap(
unsigned int controlQubit,
unsigned int targetQubit) {
424 if (obj)
return lib->MPSApplySwap(obj, controlQubit, targetQubit);
429 bool ApplyCX(
unsigned int controlQubit,
unsigned int targetQubit) {
430 if (obj)
return lib->MPSApplyCX(obj, controlQubit, targetQubit);
435 bool ApplyCY(
unsigned int controlQubit,
unsigned int targetQubit) {
436 if (obj)
return lib->MPSApplyCY(obj, controlQubit, targetQubit);
441 bool ApplyCZ(
unsigned int controlQubit,
unsigned int targetQubit) {
442 if (obj)
return lib->MPSApplyCZ(obj, controlQubit, targetQubit);
447 bool ApplyCH(
unsigned int controlQubit,
unsigned int targetQubit) {
448 if (obj)
return lib->MPSApplyCH(obj, controlQubit, targetQubit);
453 bool ApplyCSX(
unsigned int controlQubit,
unsigned int targetQubit) {
454 if (obj)
return lib->MPSApplyCSX(obj, controlQubit, targetQubit);
459 bool ApplyCSXDG(
unsigned int controlQubit,
unsigned int targetQubit) {
460 if (obj)
return lib->MPSApplyCSXDG(obj, controlQubit, targetQubit);
465 bool ApplyCP(
unsigned int controlQubit,
unsigned int targetQubit,
467 if (obj)
return lib->MPSApplyCP(obj, controlQubit, targetQubit, theta);
472 bool ApplyCRx(
unsigned int controlQubit,
unsigned int targetQubit,
474 if (obj)
return lib->MPSApplyCRx(obj, controlQubit, targetQubit, theta);
479 bool ApplyCRy(
unsigned int controlQubit,
unsigned int targetQubit,
481 if (obj)
return lib->MPSApplyCRy(obj, controlQubit, targetQubit, theta);
486 bool ApplyCRz(
unsigned int controlQubit,
unsigned int targetQubit,
488 if (obj)
return lib->MPSApplyCRz(obj, controlQubit, targetQubit, theta);
493 bool ApplyCU(
unsigned int controlQubit,
unsigned int targetQubit,
494 double theta,
double phi,
double lambda,
double gamma) {
496 return lib->MPSApplyCU(obj, controlQubit, targetQubit, theta, phi, lambda,
503 GpuDeviceContext lib;
int ApplyK(void *sim, int qubit)
int RestoreState(void *sim)
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 ApplyCSXDG(void *sim, int controlQubit, int targetQubit)
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 ApplySXDG(void *sim, int qubit)
int ApplySDG(void *sim, int qubit)
unsigned long long int Measure(void *sim, const unsigned long int *qubits, unsigned long int nrQubits)
int ApplyY(void *sim, int qubit)
double * Amplitude(void *sim, unsigned long long int outcome)
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 ApplySX(void *sim, int qubit)
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)
int ApplyCSX(void *sim, int controlQubit, int targetQubit)