@@ -144,7 +144,8 @@ The bigram set `B(𝒢)` encodes these endpoints as pairs:
144144`B(𝒢) ≡ {(𝓁(g₁),𝓇(g₁)),…,(𝓁(gₙ),𝓇(gₙ))}`
145145
146146The clipped gauge `𝒢` is a specific choice of stabilizer state where exactly two stabilizer endpoints exist at each site,
147- ensuring `ρ𝓁(x) + ρ𝓇(x) = 2` for all sites `x`.
147+ ensuring `ρₗ(x) + ρᵣ(x) = 2` for all sites `x` where `ρ` represents the reduced density matrix for the subsystem under
148+ consideration.
148149
149150In the clipped gauge, entanglement entropy is determined only by the stabilizers' endpoints, regardless of their internal structure.
150151
@@ -187,26 +188,12 @@ end
187188"""
188189$TYPEDSIGNATURES
189190
190- Get bipartite entanglement entropy of a subsystem `𝒶`.
191+ Get bipartite entanglement entropy of a subsystem
191192
192- In a system of `n`-qubits divided into regions `𝒶` and `𝒷`, the Rényi (or von Neumann)
193- entropy `S(ρ𝒶)` where `ρ𝒶` is reduced density matrix, quantifies the quantum information
194- in region `𝒶` after tracing out region `𝒷`.
193+ Defined as entropy of the reduced density matrix.
195194
196- The entropy is given by: `S(ρ𝒶) = |𝒶| - log₂ |𝒢𝒶|`, where `𝒢𝒶` is a subgroup of stabilizers
197- acting non-trivially on `𝒶`. This entropy measures the number of independent stabilizers
198- on `𝒶`, reflecting the quantum correlations between regions.
199-
200- The stabilizer group `𝒢`, viewed as a binary vector space `V`, can be decomposed such that:
201- `S𝒶 = |𝒷| - dim V𝒷 = dim (Π𝒶 V) - |𝒶|` where `Π𝒶` and `Π𝒷` are truncation maps for regions
202- `𝒶` and `𝒷`, respectively.
203-
204- Initially, each site has one stabilizer and zero entanglement, but as stabilizers enter
205- region `𝒶` over time, entanglement `S𝒶` increases by one bit for each new independent
206- operator in `𝒶`.
207-
208- It can be calculated with multiple different algorithms, the most performant one depending
209- on the particular case.
195+ It can be calculated with multiple different algorithms,
196+ the most performant one depending on the particular case.
210197
211198Currently implemented are the `:clip` (clipped gauge), `:graph` (graph state), and `:rref` (Gaussian elimination) algorithms.
212199Benchmark your particular case to choose the best one.
@@ -224,13 +211,24 @@ Get bipartite entanglement entropy of a contiguous subsystem by passing through
224211If `clip=false` is set the canonicalization step is skipped, useful if the input state is already in the clipped gauge.
225212
226213```jldoctest
214+ julia> using Graphs # hide
215+
227216julia> s = ghz(3)
228217+ XXX
229218+ ZZ_
230219+ _ZZ
231220
232221julia> entanglement_entropy(s, 1:3, Val(:clip))
2332220
223+
224+ julia> s = Stabilizer(Graph(ghz(4)))
225+ + XZZZ
226+ + ZX__
227+ + Z_X_
228+ + Z__X
229+
230+ julia> entanglement_entropy(s, [1,4], Val(:graph))
231+ 1
234232```
235233
236234See also: [`bigram`](@ref), [`canonicalize_clip!`](@ref)
@@ -250,19 +248,6 @@ $TYPEDSIGNATURES
250248
251249Get bipartite entanglement entropy by first converting the state to a graph and computing the rank of the adjacency matrix.
252250
253- ```jldoctest
254- julia> using Graphs # hide
255-
256- julia> s = Stabilizer(Graph(ghz(4)))
257- + XZZZ
258- + ZX__
259- + Z_X_
260- + Z__X
261-
262- julia> entanglement_entropy(s, [1,4], Val(:graph))
263- 1
264- ```
265-
266251Based on "Entanglement in graph states and its applications".
267252""" # TODO you should use [hein2006entanglement](@cite) instead of "Entanglement in graph states and its applications", but Documenter is giving the weirdest error if you do so...
268253function entanglement_entropy (state:: AbstractStabilizer , subsystem:: AbstractVector , algorithm:: Val{:graph} )
@@ -281,20 +266,7 @@ Get bipartite entanglement entropy by converting to RREF form (i.e., partial tra
281266
282267The state will be partially canonicalized in an RREF form.
283268
284- ```jldoctest
285- julia> s = MixedDestabilizer(T"-IX -YX -ZZ -ZI",2)
286- 𝒟ℯ𝓈𝓉𝒶𝒷
287- - _X
288- - YX
289- 𝒮𝓉𝒶𝒷
290- - ZZ
291- - Z_
292-
293- julia> entanglement_entropy(s, [1,2], Val(:rref))
294- 0
295- ```
296-
297- See also: [`canonicalize_rref!`](@ref), [`traceout!`](@ref).
269+ See also: [`canonicalize_rref!`](@ref), [`traceout!`](@ref), [`mutual_information`](@ref)
298270"""
299271function entanglement_entropy (state:: AbstractStabilizer , subsystem:: AbstractVector , algorithm:: Val{:rref} ; pure:: Bool = false )
300272 nb_of_qubits = nqubits (state)
@@ -310,39 +282,20 @@ function entanglement_entropy(state::AbstractStabilizer, subsystem::AbstractVect
310282 return nb_of_qubits - rank_after_deletion - nb_of_deletions
311283end
312284
313- """
314- $TYPEDSIGNATURES
315- """
316285entanglement_entropy (state:: MixedDestabilizer , subsystem:: AbstractVector , a:: Val{:rref} ) = entanglement_entropy (state, subsystem, a; pure= nqubits (state)== rank (state))
317286
318287_to_unitrange (x) = isa (x, UnitRange) ? x : isa (x, AbstractVector) && ! isempty (x) && all (diff (x) .== 1 ) ? UnitRange (first (x), last (x)) : error (" Cannot convert to UnitRange: $x " )
319288
320289"""
321290$TYPEDSIGNATURES
322291
323- The mutual information between subsystems `𝒶` and `𝒷` in a stabilizer state is
324- given by `Iⁿ(𝒶, 𝒷) = Sⁿ𝒶 + Sⁿ𝒷 - Sⁿ𝒶𝒷`, where the Rényi index `n` is dropped because, for
325- Clifford circuits, all Renyi entropies are equal due to the flat entanglement spectrum.
292+ The mutual information between subsystems `𝒶` and `𝒷` in a stabilizer state is given by `I(𝒶, 𝒷) = S𝒶 + S𝒷 - S𝒶𝒷`.
326293
327294```jldoctest
295+ julia> using Graphs # hide
296+
328297julia> mutual_information(ghz(3), 1:2, 3:4, Val(:clip))
3292982
330- ```
331-
332- See Eq. E6 of [li2019measurement](@cite).
333- """
334- function mutual_information (state:: AbstractStabilizer , A:: UnitRange , B:: UnitRange , algorithm:: Val{:clip} ; clip:: Bool = true )
335- S𝒶 = entanglement_entropy (state, A, algorithm; clip= clip)
336- S𝒷 = entanglement_entropy (state, B, algorithm; clip= clip)
337- S𝒶𝒷 = entanglement_entropy (state, _to_unitrange (union (A, B)), algorithm; clip= clip)
338- return S𝒶 + S𝒷 - S𝒶𝒷
339- end
340-
341- """
342- $TYPEDSIGNATURES
343-
344- ```jldoctest
345- julia> using Graphs # hide
346299
347300julia> s = Stabilizer(Graph(ghz(4)))
348301+ XZZZ
@@ -354,17 +307,34 @@ julia> mutual_information(s, [1,2], [3, 4], Val(:graph))
3543072
355308```
356309
310+ See Eq. E6 of [li2019measurement](@cite). See also: [`entanglement_entropy`](@ref)
357311"""
358- function mutual_information (state:: AbstractStabilizer , A:: AbstractVector , B:: AbstractVector , algorithm:: Union{Val{:rref}, Val{:graph}} ; pure:: Bool = false )
359- if algorithm == Val (:graph )
360- S𝒶 = entanglement_entropy (state, A, algorithm)
361- S𝒷 = entanglement_entropy (state, B, algorithm)
362- S𝒶𝒷 = entanglement_entropy (state, union (A, B), algorithm)
363- return S𝒶 + S𝒷 - S𝒶𝒷
364- else
365- S𝒶 = entanglement_entropy (state, A, algorithm; pure= pure)
366- S𝒷 = entanglement_entropy (state, B, algorithm; pure= pure)
367- S𝒶𝒷 = entanglement_entropy (state, union (A, B), algorithm; pure= pure)
368- return S𝒶 + S𝒷 - S𝒶𝒷
312+ function mutual_information (state:: AbstractStabilizer , A:: UnitRange , B:: UnitRange , algorithm:: Val{:clip} ; clip:: Bool = true )
313+ if ! isempty (intersect (A, B))
314+ throw (ArgumentError (" Ranges A and B must not overlap." ))
315+ end
316+ S𝒶 = entanglement_entropy (state, A, algorithm; clip= clip)
317+ S𝒷 = entanglement_entropy (state, B, algorithm; clip= clip)
318+ S𝒶𝒷 = entanglement_entropy (state, _to_unitrange (union (A, B)), algorithm; clip= clip)
319+ return S𝒶 + S𝒷 - S𝒶𝒷
320+ end
321+
322+ function mutual_information (state:: AbstractStabilizer , A:: AbstractVector , B:: AbstractVector , algorithm:: Val{:rref} ; pure:: Bool = false )
323+ if ! isempty (intersect (A, B))
324+ throw (ArgumentError (" Ranges A and B must not overlap." ))
325+ end
326+ S𝒶 = entanglement_entropy (state, A, algorithm; pure= pure)
327+ S𝒷 = entanglement_entropy (state, B, algorithm; pure= pure)
328+ S𝒶𝒷 = entanglement_entropy (state, union (A, B), algorithm; pure= pure)
329+ return S𝒶 + S𝒷 - S𝒶𝒷
330+ end
331+
332+ function mutual_information (state:: AbstractStabilizer , A:: AbstractVector , B:: AbstractVector , algorithm:: Val{:graph} )
333+ if ! isempty (intersect (A, B))
334+ throw (ArgumentError (" Ranges A and B must not overlap." ))
369335 end
336+ S𝒶 = entanglement_entropy (state, A, algorithm)
337+ S𝒷 = entanglement_entropy (state, B, algorithm)
338+ S𝒶𝒷 = entanglement_entropy (state, union (A, B), algorithm)
339+ return S𝒶 + S𝒷 - S𝒶𝒷
370340end
0 commit comments