-
Notifications
You must be signed in to change notification settings - Fork 186
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #1207 from khalatepradnya/align-with-main
[experimental/python] Align with mainline
- Loading branch information
Showing
44 changed files
with
1,605 additions
and
197 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -51,6 +51,7 @@ MSB | |
Max-Cut | ||
MyST | ||
NGC | ||
NVCF | ||
NVIDIA | ||
NVQIR | ||
OQC | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,49 @@ | ||
// Compile and run with: | ||
// ``` | ||
// nvq++ --target nvcf nvcf_sample.cpp -o out.x | ||
// ./out.x | ||
// ``` | ||
// Assumes a valid NVCF API key and function ID have been stored in environment | ||
// variables or `~/.nvcf_config` file. Alternatively, they can be set in the | ||
// command line like below. | ||
// ``` | ||
// nvq++ --target nvcf --nvcf-api-key <YOUR API KEY> --nvcf-function-id \ | ||
// <NVCF function Id> nvcf_sample.cpp -o out.x | ||
// ./out.x | ||
// ``` | ||
// Please refer to the documentations for information about how to attain NVCF | ||
// information. | ||
|
||
#include <cudaq.h> | ||
#include <iostream> | ||
|
||
// Define a simple quantum kernel to execute on NVCF. | ||
struct ghz { | ||
// Maximally entangled state between 25 qubits. | ||
auto operator()() __qpu__ { | ||
constexpr int NUM_QUBITS = 25; | ||
cudaq::qvector q(NUM_QUBITS); | ||
h(q[0]); | ||
for (int i = 0; i < NUM_QUBITS - 1; i++) { | ||
x<cudaq::ctrl>(q[i], q[i + 1]); | ||
} | ||
auto result = mz(q); | ||
} | ||
}; | ||
|
||
int main() { | ||
// Submit to NVCF asynchronously (e.g., continue executing | ||
// code in the file until the job has been returned). | ||
auto async_counts_handle = cudaq::sample_async(ghz{}); | ||
// ... classical code to execute in the meantime ... | ||
std::cout << "Waiting for NVCF result...\n"; | ||
|
||
// Calling .get() on the handle to synchronize the result. | ||
auto async_counts = async_counts_handle.get(); | ||
async_counts.dump(); | ||
|
||
// OR: Submit to NVCF synchronously (e.g., wait for the job | ||
// result to be returned before proceeding). | ||
auto counts = cudaq::sample(ghz{}); | ||
counts.dump(); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,32 @@ | ||
// Compile and run with: | ||
// ``` | ||
// nvq++ --target nvcf --nvcf-backend tensornet nvcf_state.cpp -o out.x | ||
// ./out.x | ||
// ``` | ||
// Assumes a valid NVCF API key and function ID have been stored in environment | ||
// variables or `~/.nvcf_config` file. Alternatively, they can be set in the | ||
// command line like below. | ||
// ``` | ||
// nvq++ --target nvcf --nvcf-backend tensornet --nvcf-api-key <YOUR API KEY> \ | ||
// --nvcf-function-id <NVCF function Id> nvcf_state.cpp -o out.x | ||
// ./out.x | ||
// ``` | ||
// Please refer to the documentations for information about how to attain NVCF | ||
// information. | ||
|
||
#include "cudaq/algorithms/state.h" | ||
#include <cudaq.h> | ||
#include <iostream> | ||
|
||
int main() { | ||
auto kernel = cudaq::make_kernel(); | ||
const std::size_t NUM_QUBITS = 20; | ||
auto q = kernel.qalloc(NUM_QUBITS); | ||
kernel.h(q[0]); | ||
for (std::size_t qId = 0; qId < NUM_QUBITS - 1; ++qId) | ||
kernel.x<cudaq::ctrl>(q[qId], q[qId + 1]); | ||
auto state = cudaq::get_state(kernel); | ||
std::cout << "Amplitude(00..00) = " << state[0] << "\n"; | ||
std::cout << "Amplitude(11..11) = " << state[(1ULL << NUM_QUBITS) - 1] | ||
<< "\n"; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,60 @@ | ||
// Compile and run with: | ||
// ``` | ||
// nvq++ --target nvcf --nvcf-nqpus 3 nvcf_vqe.cpp -o out.x | ||
// ./out.x | ||
// ``` | ||
// Note: we set `nqpus` to 3 to establish 3 concurrent NVCF job submission | ||
// pipes. Assumes a valid NVCF API key and function ID have been stored in | ||
// environment variables or `~/.nvcf_config` file. Alternatively, they can be | ||
// set in the command line like below. | ||
// ``` | ||
// nvq++ --target nvcf --nvcf-nqpus 3 --nvcf-api-key <YOUR API KEY> \ | ||
// --nvcf-function-id <NVCF function Id> nvcf_vqe.cpp -o out.x | ||
// ./out.x | ||
// ``` | ||
// Please refer to the documentations for information about how to attain NVCF | ||
// information. | ||
|
||
#include <cudaq.h> | ||
#include <cudaq/algorithm.h> | ||
#include <cudaq/gradients.h> | ||
#include <cudaq/optimizers.h> | ||
#include <iostream> | ||
|
||
int main() { | ||
using namespace cudaq::spin; | ||
cudaq::spin_op h = 5.907 - 2.1433 * x(0) * x(1) - 2.1433 * y(0) * y(1) + | ||
.21829 * z(0) - 6.125 * z(1); | ||
|
||
auto [ansatz, theta] = cudaq::make_kernel<double>(); | ||
auto q = ansatz.qalloc(); | ||
auto r = ansatz.qalloc(); | ||
ansatz.x(q); | ||
ansatz.ry(theta, r); | ||
ansatz.x<cudaq::ctrl>(r, q); | ||
|
||
// Run VQE with a gradient-based optimizer. | ||
// Delegate cost function and gradient computation across different NVCF-based | ||
// QPUs. Note: depending on the user's account, there might be different | ||
// number of NVCF worker instances available. Hence, although we're making | ||
// concurrent job submissions across multiple QPUs, the speedup would be | ||
// determined by the number of NVCF worker instances. | ||
cudaq::optimizers::lbfgs optimizer; | ||
auto [opt_val, opt_params] = optimizer.optimize( | ||
/*dim=*/1, /*opt_function*/ [&](const std::vector<double> ¶ms, | ||
std::vector<double> &grads) { | ||
// Queue asynchronous jobs to do energy evaluations across multiple QPUs | ||
auto energy_future = | ||
cudaq::observe_async(/*qpu_id=*/0, ansatz, h, params[0]); | ||
const double paramShift = M_PI_2; | ||
auto plus_future = cudaq::observe_async(/*qpu_id=*/1, ansatz, h, | ||
params[0] + paramShift); | ||
auto minus_future = cudaq::observe_async(/*qpu_id=*/2, ansatz, h, | ||
params[0] - paramShift); | ||
grads[0] = (plus_future.get().expectation() - | ||
minus_future.get().expectation()) / | ||
2.0; | ||
return energy_future.get().expectation(); | ||
}); | ||
std::cout << "Minimum energy = " << opt_val << " (expected -1.74886).\n"; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,29 @@ | ||
import cudaq | ||
|
||
# This example assumes the NVCF API key and Function Id have been set in the `~/.nvcf_config` file/environment variables. | ||
# If not, you can set the API Key and Function ID environment variables in the Python script with: | ||
# ``` | ||
# os.environ["NVCF_API_KEY"] = "<YOUR NVCF API KEY>"` | ||
# os.environ["NVCF_FUNCTION_ID"] = "<YOUR NVCF FUNCTION ID>" | ||
# ``` | ||
# Alternatively, the `api_key` and `function_id` values can be passed to the target directly, | ||
# ``` | ||
# cudaq.set_target("nvcf", | ||
# backend="tensornet", | ||
# api_key="<YOUR NVCF API KEY>" | ||
# function_id="<YOUR NVCF FUNCTION ID>") | ||
# ``` | ||
cudaq.set_target("nvcf", backend="tensornet") | ||
|
||
num_qubits = 50 | ||
kernel = cudaq.make_kernel() | ||
qubits = kernel.qalloc(num_qubits) | ||
# Place qubits in superposition state. | ||
kernel.h(qubits[0]) | ||
for i in range(num_qubits - 1): | ||
kernel.cx(qubits[i], qubits[i + 1]) | ||
# Measure. | ||
kernel.mz(qubits) | ||
|
||
counts = cudaq.sample(kernel, shots_count=100) | ||
print(counts) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,27 @@ | ||
import cudaq | ||
|
||
# This example assumes the NVCF API key and Function Id have been set in the `~/.nvcf_config` file/environment variables. | ||
# If not, you can set the API Key and Function ID environment variables in the Python script with: | ||
# ``` | ||
# os.environ["NVCF_API_KEY"] = "<YOUR NVCF API KEY>"` | ||
# os.environ["NVCF_FUNCTION_ID"] = "<YOUR NVCF FUNCTION ID>" | ||
# ``` | ||
# Alternatively, the `api_key` and `function_id` values can be passed to the target directly, | ||
# ``` | ||
# cudaq.set_target("nvcf", | ||
# api_key="<YOUR NVCF API KEY>" | ||
# function_id="<YOUR NVCF FUNCTION ID>") | ||
# ``` | ||
cudaq.set_target("nvcf") | ||
|
||
num_qubits = 20 | ||
kernel = cudaq.make_kernel() | ||
qubits = kernel.qalloc(num_qubits) | ||
# Place qubits in GHZ state. | ||
kernel.h(qubits[0]) | ||
for i in range(num_qubits - 1): | ||
kernel.cx(qubits[i], qubits[i + 1]) | ||
|
||
state = cudaq.get_state(kernel) | ||
print("Amplitude(00..00) =", state[0]) | ||
print("Amplitude(11..11) =", state[2**num_qubits - 1]) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,62 @@ | ||
import cudaq | ||
from cudaq import spin | ||
import math | ||
|
||
# This example assumes the NVCF API key and Function Id have been set in the `~/.nvcf_config` file/environment variables. | ||
# If not, you can set the API Key and Function ID environment variables in the Python script with: | ||
# ``` | ||
# os.environ["NVCF_API_KEY"] = "<YOUR NVCF API KEY>"` | ||
# os.environ["NVCF_FUNCTION_ID"] = "<YOUR NVCF FUNCTION ID>" | ||
# ``` | ||
# Alternatively, the `api_key` and `function_id` values can be passed to the target directly, | ||
# ``` | ||
# cudaq.set_target("nvcf", | ||
# nqpus=3, | ||
# api_key="<YOUR NVCF API KEY>" | ||
# function_id="<YOUR NVCF FUNCTION ID>") | ||
# ``` | ||
cudaq.set_target("nvcf", nqpus=3) | ||
|
||
print("Number of QPUs:", cudaq.get_target().num_qpus()) | ||
# Note: depending on the user's account, there might be different | ||
# number of NVCF worker instances available. Hence, although we're making | ||
# concurrent job submissions across multiple QPUs, the speedup would be | ||
# determined by the number of NVCF worker instances. | ||
# Create the parameterized ansatz | ||
kernel, theta = cudaq.make_kernel(float) | ||
qreg = kernel.qalloc(2) | ||
kernel.x(qreg[0]) | ||
kernel.ry(theta, qreg[1]) | ||
kernel.cx(qreg[1], qreg[0]) | ||
|
||
# Define its spin Hamiltonian. | ||
hamiltonian = (5.907 - 2.1433 * spin.x(0) * spin.x(1) - | ||
2.1433 * spin.y(0) * spin.y(1) + 0.21829 * spin.z(0) - | ||
6.125 * spin.z(1)) | ||
|
||
|
||
def opt_gradient(parameter_vector): | ||
# Evaluate energy and gradient on different remote QPUs | ||
# (i.e., concurrent job submissions to NVCF) | ||
energy_future = cudaq.observe_async(kernel, | ||
hamiltonian, | ||
parameter_vector[0], | ||
qpu_id=0) | ||
plus_future = cudaq.observe_async(kernel, | ||
hamiltonian, | ||
parameter_vector[0] + 0.5 * math.pi, | ||
qpu_id=1) | ||
minus_future = cudaq.observe_async(kernel, | ||
hamiltonian, | ||
parameter_vector[0] - 0.5 * math.pi, | ||
qpu_id=2) | ||
return (energy_future.get().expectation(), [ | ||
(plus_future.get().expectation() - minus_future.get().expectation()) / | ||
2.0 | ||
]) | ||
|
||
|
||
optimizer = cudaq.optimizers.LBFGS() | ||
optimal_value, optimal_parameters = optimizer.optimize(1, opt_gradient) | ||
print("Ground state energy =", optimal_value) | ||
print("Optimal parameters =", optimal_parameters) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.