五. 量子近似优化算法 (QAOA)
量子近似优化算法 (Quantum Approximate Optimization Algorithm) 可以处理的问题中最著名的一个是名为 MaxCut 的图论问题
给定一个图,求一个图的最大分割。
此处分割的大小定义为将图划分为两部分,割过边的数目的多少。它的判定版本被证明是 NP-Complete 问题
给定一个图和整数 k,问是否有存在一个分割大于等于 k。
它可以被翻译为求解经典Ising模型基态的问题,其Hamiltonian如下
E 是一个图中边的集合,可以把定义在顶角 V 上的自旋 理解为一种将图的二分割,+1 和 -1 分别代表了分割后的两部分,分割的大小为所有端点自旋符号相反的边的数目。根据上面的Hamiltonian形式,实际程序的 loss函数可以被定义为
这里去掉了常数项,并且取反号使目标变成求极小。这里引入了权重 ,将MaxCut问题拓展到了带权重版本。特别的地方在于,它通过参数化量子波函数
来变分求解经典Hamilton的基态(是个直积态),避免了直接操作离散数据。
求解这个问题,QAOA 采用了经典量子混合算法,量子部分负责构造量子线路 ansatz ,计算loss。作为一个可以在D-wave 这种量子模拟器上跑的算法,它的 ansatz 的设计是受量子退火算法影响的,其参数化形式为
其中 为
和
的集合,是需要优化的参数。
,
,
为横场Hamiltonian。
为各种构型均匀叠加的初始态。简而言之,就是依次作用系统Hamiltonian和横场项到量子态上,以作用时间为优化参数,希望最后能演化到目标经典Hamiltonian基态。经典部分负责优化,可以基于梯度也可以不基于梯度。简单起见,我们采用不基于梯度的方式去模拟,文中采用的是COBYLA算法。
参考文献:
A Quantum Approximate Optimization Algorithm首先导入一些包,其中 NLopt 是非线性优化器的包,在这个例子面我们将会使用基于单纯形法的 COBYLA 优化算法作为我们的经典优化部分。同时我们引入maxcut_gw.jl
这个文件,它包含了 MaxCut 问题的经典解法 - Goemans-Williamson 算法,具体见目录。
首先,我们构造两个Hamiltonian构造方法 HB 和 HC。
using Yao, BitBasis
using NLopt
include("maxcut_gw.jl")
"""
Transverse field term
"""
HB(nbit::Int) = sum([put(nbit, i=>X) for i=1:nbit])
"""
Target Hamiltonian.
"""
function HC(W::AbstractMatrix)
nbit = size(W, 1)
ab = Any[]
for i=1:nbit,j=i+1:nbit
if W[i,j] != 0
push!(ab, 0.5*W[i,j]*repeat(nbit, Z, [i,j]))
end
end
sum(ab)
end
对于三个角的图,HB 定义的含时演化如下
julia> TimeEvolution(HB(3), 0.1)
Time Evolution Total: 3, DataType: Complex{Float64}
+
├─ put on (1)
│ └─ X gate
├─ put on (2)
│ └─ X gate
└─ put on (3)
└─ X gate
Δt = 0.1, tol = 1.0e-7
HC通过权重矩阵生成,比如如下的 3 个角的的全连接图
julia> W = [0 1 3; 1 0 1; 3 1 0] # 3x3 的全连接图
3×3 Array{Int64,2}:
0 1 3
1 0 1
3 1 0
julia> hc = HC(W)
Total: 3, DataType: Complex{Float64}
+
├─ [0.5] repeat on (1, 2)
│ └─ Z gate
├─ [1.5] repeat on (1, 3)
│ └─ Z gate
└─ [0.5] repeat on (2, 3)
└─ Z gate
julia> ishermitian(hc)
true
下来可以构造 QAOA 整体的线路图,此处depth
定义为 ,
的重复次数。可选参数
use_cache
如果为true
,则可以把Hamiltonian的矩阵形式缓存下来加速含时演化操作。
function qaoa_circuit(W::AbstractMatrix, depth::Int; use_cache::Bool=false)
nbit = size(W, 1)
hb = HB(nbit)
hc = HC(W)
use_cache && (hb = hb |> cache; hc = hc |> cache)
c = chain(nbit, [repeat(nbit, H, 1:nbit)])
append!(c, [chain(nbit, [time_evolve(hc, 0.0, tol=1e-5),
time_evolve(hb, 0.0, tol=1e-5)]) for i=1:depth])
end
可以看到对于3个node的全连接图,两层的结构最后得到的线路图如下
julia> qaoa_circuit(W, 2)
Total: 3, DataType: Complex{Float64}
chain
├─ repeat on (1, 2, 3)
│ └─ H gate
├─ chain
│ ├─ Time Evolution Total: 3, DataType: Complex{Float64}
│ │ +
│ │ ├─ [0.5] repeat on (1, 2)
│ │ │ └─ Z gate
│ │ ├─ [1.5] repeat on (1, 3)
│ │ │ └─ Z gate
│ │ └─ [0.5] repeat on (2, 3)
│ │ └─ Z gate
│ │ Δt = 0.0, tol = 1.0e-5
│ └─ Time Evolution Total: 3, DataType: Complex{Float64}
│ +
│ ├─ put on (1)
│ │ └─ X gate
│ ├─ put on (2)
│ │ └─ X gate
│ └─ put on (3)
│ └─ X gate
│ Δt = 0.0, tol = 1.0e-5
└─ chain
├─ Time Evolution Total: 3, DataType: Complex{Float64}
│ +
│ ├─ [0.5] repeat on (1, 2)
│ │ └─ Z gate
│ ├─ [1.5] repeat on (1, 3)
│ │ └─ Z gate
│ └─ [0.5] repeat on (2, 3)
│ └─ Z gate
│ Δt = 0.0, tol = 1.0e-5
└─ Time Evolution Total: 3, DataType: Complex{Float64}
+
├─ put on (1)
│ └─ X gate
├─ put on (2)
│ └─ X gate
└─ put on (3)
└─ X gate
Δt = 0.0, tol = 1.0e-5
训练采用COBYLA算法,是基于单纯形方法的优化算法中比较好用的。用法请参见NLopt的文档。
function cobyla_optimize(circuit::MatrixBlock{N}, hc::MatrixBlock; niter::Int) where N
function f(params, grad)
reg = zero_state(N) |> dispatch!(circuit, params)
loss = expect(hc, reg) |> real
#println(loss)
loss
end
opt = Opt(:LN_COBYLA, nparameters(circuit))
min_objective!(opt, f)
maxeval!(opt, niter)
cost, params, info = optimize(opt, parameters(circuit))
pl = zero_state(N) |> circuit |> probs
cost, params, pl
end
作为测试,我们构造一个5个节点的图

nbit = 5
W = [0 5 2 1 0;
5 0 3 2 0;
2 3 0 0 0;
1 2 0 0 4;
0 0 0 4 0]
# the exact solution
exact_cost, sets = goemansWilliamson(W)
hc = HC(W)
# the cut is -<Hc> + sum(wij)/2
@test -expect(hc, product_state(5, bmask(sets[1]...)))+sum(W)/4 ≈ exact_cost
这里我们会得到严格解[1, 3, 4],[2, 5]
, 此分割大小为14
. 这里我们测试了目标 Hamiltonian的正确性,注意这里符号和常数的差别。
# build a QAOA circuit and start training.
qc = qaoa_circuit(W, 20; use_cache=false)
opt_pl = nothing
opt_cost = Inf
for i = 1:10
dispatch!(qc, :random)
cost, params, pl = cobyla_optimize(qc, hc; niter=2000)
@show cost
cost < opt_cost && (opt_pl = pl)
end
输入如下:
cost=-5.056439885146659
cost=-5.3148313277163455
cost=-5.314515402351343
cost=-5.27061216619153
cost=-5.218577446603341
cost=-5.140030583281352
cost=-4.859469398853606
cost=-5.445797991390686
cost=-5.2074338799039
cost=-4.971171116896116
对于严格解,cost应该是-5.5,可见经过充分优化,很多情况QAOA都可以得到足够好的解。
检查输出是否正确
# check the correctness of result
config = argmax(opt_pl)-1
@test config in [bmask(set...) for set in sets]
大家有没有发现其实QAOA优化有时候不稳定,经常得到的结果是错的?一个可以优化的地方是用基于梯度的优化器,但是这需要很特别的构造。大家可以去尝试哦~
Goemans-Williamson 算法
该算法用于求解Max-Cut问题,原算法在 https://github.com/ericproffitt/MaxCut, 但是由于很久没更新已经不再兼容Julia 1.0以上版本。如下是适用于Julia1.x的代码,需要提前安装CSC和Convex两个包来使用。
using Convex
using SCS
using LinearAlgebra
"
The Goemans-Williamson algorithm for the MAXCUT problem.
Adapted From: https://github.com/ericproffitt/MaxCut
"
function goemansWilliamson(W::Matrix{T}; tol::Real=1e-1, iter::Int=100) where T<:Real
"Partition a graph into two disjoint sets such that the sum of the edge weights
which cross the partition is as large as possible (known to be NP-hard)."
"A cut of a graph can be produced by assigning either 1 or -1 to each vertex. The Goemans-Williamson
algorithm relaxes this binary condition to allow for vector assignments drawn from the (n-1)-sphere
(choosing an n-1 dimensional space will ensure seperability). This relaxation can then be written as
an SDP. Once the optimal vector assignments are found, origin centered hyperplanes are generated and
their corresponding cuts evaluated. After 'iter' trials, or when the desired tolerance is reached,
the hyperplane with the highest corresponding binary cut is used to partition the vertices."
"W: Adjacency matrix."
"tol: Maximum acceptable distance between a cut and the MAXCUT upper bound."
"iter: Maximum number of hyperplane iterations before a cut is chosen."
LinearAlgebra.checksquare(W)
@assert LinearAlgebra.issymmetric(W) "Adjacency matrix must be symmetric."
@assert all(W .>= 0) "Entries of the adjacency matrix must be nonnegative."
@assert all(diag(W) .== 0) "Diagonal entries of adjacency matrix must be zero."
@assert tol > 0 "The tolerance 'tol' must be positive."
@assert iter > 0 "The number of iterations 'iter' must be a positive integer."
"This is the standard SDP Relaxation of the MAXCUT problem, a reference can be found at
http://www.sfu.ca/~mdevos/notes/semidef/GW.pdf."
k = size(W, 1)
S = Semidefinite(k)
expr = dot(W, S)
constr = [S[i,i] == 1.0 for i in 1:k]
problem = minimize(expr, constr...)
solve!(problem, SCSSolver(verbose=0))
### Ensure symmetric positive-definite.
A = 0.5 * (S.value + S.value')
A += (max(0, -eigmin(A)) + eps(1e3))*I
X = Matrix(cholesky(A))
### A non-trivial upper bound on MAXCUT.
upperbound = (sum(W) - dot(W, S.value)) / 4
"Random origin-centered hyperplanes, generated to produce partitions of the graph."
maxcut = 0
maxpartition = nothing
for i in 1:iter
gweval = X' * randn(k)
partition = (findall(x->x>0, gweval), findall(x->x<0, gweval))
cut = sum(W[partition...])
if cut > maxcut
maxpartition = partition
maxcut = cut
end
upperbound - maxcut < tol && break
i == iter && println("Max iterations reached.")
end
return round(maxcut; digits=3), maxpartition
end
using Test
@testset "max cut" begin
W = [0 5 2 1 0;
5 0 3 2 0;
2 3 0 0 0;
1 2 0 0 4;
0 0 0 4 0]
maxcut, maxpartition = goemansWilliamson(W)
@test maxcut == 14
@test [2,5] in maxpartition
end
热门文章排行
- 共享,正从风口到风险
- 走进涂料市场的秘密
- 在人工智能炒热机器人时,也被人把风带进了
- 生物涂料有什么好处?
- 智能音箱,正走在智能手表的老路上
- “去乐视化”之后,新易到的机会在哪儿?
- 世界十大假戏真做的电影排行榜 真枪实弹太
- 日本十大波涛汹涌巨乳美少女第5名,凶悍!
- 涂料行业未来走势 品质与个性化不可少
- 打造时尚靓丽居室 油漆选购注意三点
最新资讯文章
- 留学写作参考:推荐信中的优点、不足写什么
- 2024年高考志愿,选哪些专业将来好就业
- 张雪峰建议女生选的专业 什么专业最适合女
- 读懂中外合办硕士!优势是什么?
- 留学生专业好就业的大学
- 英语专业考研可以跨考哪些专业?
- 英国哪些城市最适合中国留学生?八大留学热
- 出国留学推荐信范文【两篇】
- 2023年出国导师推荐信 留学基金委导师
- 出国留学读研究生如何申请?各个国家研究生
- 萨塞克斯大学
- 音乐专业出国留学英语怎么要求的(音乐专业
- 中学生留学有哪些好处?
- 考研与就业,你会怎样抉择?
- 2025学科英语考研学校排名出炉!考生报
- 西班牙留学 圣帕布洛大学的基本介绍
- 美术留学国家推荐,美术生出国留学哪个国家
- 英语专业的学生赴英留学可以选择什么专业?
- 美国研究生留学申请条件
- 出国留学有什么好处?_5