8个版本
0.3.7 | 2023年9月8日 |
---|---|
0.3.6 | 2023年8月23日 |
0.3.4 | 2023年7月28日 |
#14 in 仿真
每月下载量76次
3MB
30K SLoC
quest_bind
QuEST v3.5.0的包装器。
量子精确仿真工具包(QuEST)是一个无冗余、追求速度的量子电路仿真器 [1]。它以MIT许可证分发。
如何使用
初始化一个新的二进制crate
cargo new tryme
cd tryme/
将 quest_bind
添加到项目的依赖项
cargo add quest_bind
现在编写一些代码并将其放入 ./src/main.rs
use quest_bind::*;
fn main() -> Result<(), QuestError> {
// Initialize QuEST environment and report to screen
let env = &QuestEnv::new();
env.report_quest_env();
// Create a 2-qubit register and report its parameters
let mut qureg = Qureg::try_new(2, env).expect("cannot allocate new Qureg");
qureg.report_qureg_params();
// Initialize |00> state and print out the state to screen
qureg.init_zero_state();
qureg.report_state_to_screen(0);
// Prepare a Bell state `|00> + |11>`: apply Hadamard gate
// on qubit 0, then NOT on qubit 1, controlled by qubit 0.
println!("---\nPrepare Bell state: |00> + |11>");
qureg.hadamard(0).and(qureg.controlled_not(0, 1))?;
// Measure both qubits
let outcome0 = qureg.measure(0)?;
let outcome1 = qureg.measure(1)?;
println!("Qubit \"0\" measured in state: |{outcome0}>");
println!("Qubit \"1\" measured in state: |{outcome1}>");
// Because the state was entangled, the outcomes
// should always be the same
if outcome0 == outcome1 {
println!("They match!");
Ok(())
} else {
panic!("qubits in Bell state should be perfectly correlated");
}
// At this point both `qureg` and `env` are dropped and
// the allocated memory is freed.
}
文档可在 线上 以及本地找到
cargo doc --open
最后,编译并运行程序
cargo run
你应该能看到类似的内容
EXECUTION ENVIRONMENT:
Running locally on one node
Number of ranks is 1
OpenMP enabled
Number of threads available is 8
Precision: size of qreal is 8 bytes
QUBITS:
Number of qubits is 2.
Number of amps is 4.
Number of amps per rank is 4.
---
Prepare Bell state: |00> + |11>
Qubit "0" measured in state: |0>
Qubit "1" measured in state: |0>
They match!
分布式和GPU加速模式
可以通过设置适当的特性标志在 quest_bind
中启用QuEST对MPI和GPU加速计算的支持。要启用QuEST的MPI模式,设置quest_bind
的mpi
特性。只需编辑二进制crate的Cargo.toml
[package]
name = "tryme"
version = "0.1.0"
edition = "2021"
[dependencies]
quest_bind = { features = ["mpi"] }
现在,如果你再次编译并运行上述程序,输出应该是
EXECUTION ENVIRONMENT:
Running distributed (MPI) version
Number of ranks is 1
...
特性 "gpu"
启用GPU加速模式。这两个特性是互斥的,如果同时设置了这两个标志,则特性 "mpi"
优先。
测试
要为此库运行单元测试,首先将QuEST源代码作为子模块一起克隆仓库
git clone --recurse-submodules https://github.com/marek-miller/quest_bind.git
cd quest_bind
然后运行
cargo test
请注意,quest_bind
不会运行 QuEST
的测试套件,也不会检查 QuEST
的正确性。这里的测试旨在检查是否正确调用了C API,以及Rust的类型是否安全地在FFI边界之间传递。
如果您想以单精度浮点模式运行测试套件,请确保构建脚本使用正确的类型定义重新编译 libQuEST.so
cargo clean
cargo test --features=f32
默认情况下,quest_bind
使用Rust的双精度浮点类型:f64
。请参阅下文中的 数值类型 部分。
您还可以通过运行,例如,来尝试可用的示例。
cargo run --release --example grovers_search
要查看所有可用示例的列表,请尝试
cargo run --example
性能说明
在典型情况下,当CPU使用率主要由数值计算主导而不是API调用时,使用QuEST例程直接调用程序与使用quest_bind
的类似应用程序之间应该没有可察觉的性能差异。但是,请记住,通过使用“发布”配置文件编译您的代码来启用对quest_bind
和QuEST
的优化。
cargo run --release
异常处理
在失败的情况下,QuEST通过用户可配置的全局invalidQuESTInputError()
抛出异常。默认情况下,此函数会打印错误消息并中止,这在大型分布式设置中是有问题的。
我们选择通过重新实现invalidQuESTInputError()
来捕获所有异常,使用Rust的panic
机制来展开堆栈。
此外,QuEST报告的所有错误消息都记录为错误。要查看它们,请在您的crate中添加一个记录器,例如
cargo add env_logger
然后在您的应用程序中启用日志记录
fn main() {
env_logger::init();
// (...)
}
并运行
RUST_LOG=info cargo run
有关Rust中的日志记录的更多信息,请参阅log
crate。
QuestError
类型不包含API调用在失败时返回的(可能是格式错误的)数据。只有成功的调用才能达到库用户。这是根据QuEST文档的指南故意为之的。
[失败时] 用户必须确保触发的API调用不会继续(例如,用户退出或抛出异常),否则QuEST将继续使用有效的[ sic! ]输入并可能触发段错误。
有关更多信息,请参阅Quest API。
数值类型
目前,quest_bind
使用的数值类型与QuEST在x86_64
上使用的C类型完全匹配。这是一个安全但不太可移植的策略。我们直接将Rust类型传递给QuEST而不进行转换,假设以下类型定义
pub type c_float = f32;
pub type c_double = f64;
pub type c_int = i32;
pub type c_longlong = i64;
pub type c_ulong = u64;
这应该适用于许多不同的架构。如果您的系统使用稍微不同的数值类型,quest_bind
将无法编译,除了手动更改源代码之外,您几乎无能为力。
要检查Rust安装中定义的C类型,请参阅Rust标准库中模块std::ffi
的本地文档。
rustup doc
贡献
如果您想为quest_bind
做出贡献,这里有一些需要了解的事项。
-
Rust代码库的格式与
./rustfmt.toml
中的设置一致。我们启用了rustfmt
的一些不稳定功能。要正确格式化您的补丁,您将需要Rust编译器的夜间版本。在打开pull请求之前,通过运行以下命令从代码中删除lint:just lint