Skip to content

Commit ce6e7b4

Browse files
authored
Merge pull request #139 from MSRudolph/dev
- Fix `getcoeff()` behavior for `DictStorage` term sums. `PauliSum` was affected by this and had slow lookup. - Add commutator between two `VectorPauliSum`s - In-place propagation without return, i.e., `new_psum = propagate!(circuit, psum, params)` now has the final results in `psum`, not only `new_psum`. Now `new_psum === psum`. Similarly for `truncate!()` and `merge!()`. - Implement `extractsum!()` in PropagationBase as the intended way of extracing the active main sum on a propagation cache. - Standardize `==` and `\approx` for all `AbstractTermSum`. - Implement `mult!()` for propagation caches. - Implement `merge()` and `truncate()`
2 parents 66b7e94 + 689b218 commit ce6e7b4

21 files changed

+391
-138
lines changed

Project.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
name = "PauliPropagation"
22
uuid = "293282d5-3c99-4fb6-92d0-fd3280a19750"
33
authors = ["Manuel S. Rudolph"]
4-
version = "0.7.1"
4+
version = "0.7.2"
55

66
[deps]
77
AcceleratedKernels = "6a4ca0a5-0e36-4168-a932-d9be78d558f1"

src/Base/Base.jl

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -33,11 +33,14 @@ export
3333
PropagationCache,
3434
mainsum,
3535
auxsum,
36+
extractsum!,
3637
setmainsum!,
3738
setauxsum!,
3839
swapsums!,
40+
copyswapsums!,
3941
activesize,
4042
setactivesize!,
43+
activesum,
4144
activeterms,
4245
activecoeffs,
4346
activeauxterms,
@@ -65,10 +68,10 @@ export propagate,
6568
requiresmerging
6669

6770
include("./merge.jl")
68-
export merge!, mergefunc
71+
export merge, merge!, mergefunc
6972

7073
include("./truncate.jl")
71-
export truncate!
74+
export truncate, truncate!
7275

7376

7477
include("./vectorbackend.jl")

src/Base/merge.jl

Lines changed: 21 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4,18 +4,34 @@
44
# Can be overloaded for different coefficient types.
55
mergefunc(coeff1, coeff2) = coeff1 + coeff2
66

7-
# Merge `aux_psum` into `psum` using the `merge` function. `merge` can be overloaded for different coefficient types.
8-
# Then empty `aux_psum` for the next iteration.
9-
function Base.merge!(prop_cache::AbstractPropagationCache; kwargs...)
7+
Base.merge(obj) = merge!(deepcopy(obj))
8+
9+
function Base.merge!(term_sum::TS) where TS<:AbstractTermSum
10+
return _merge!(StorageType(term_sum), term_sum)
11+
end
12+
13+
function _merge!(::DictStorage, term_sum::AbstractTermSum)
14+
# Dicts are always already merged
15+
return term_sum
16+
end
17+
18+
function _merge!(::ArrayStorage, term_sum::AbstractTermSum)
19+
prop_cache = PropagationCache(term_sum)
1020

21+
merge!(prop_cache)
22+
23+
# extracts the original input term sum
24+
return extractsum!(prop_cache, term_sum)
25+
end
26+
27+
# Merge auxsum into mainsum
28+
function Base.merge!(prop_cache::AbstractPropagationCache; kwargs...)
1129

1230
prop_cache = _merge!(StorageType(prop_cache), prop_cache; kwargs...)
1331

1432
return prop_cache
1533
end
1634

17-
# Assumptions:
18-
# TODO
1935
function _merge!(::DictStorage, prop_cache::AbstractPropagationCache; kwargs...)
2036
term_sum1 = mainsum(prop_cache)
2137
term_sum2 = auxsum(prop_cache)

src/Base/propagate.jl

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -4,11 +4,12 @@ function propagate(circuit, term_sum::AbstractTermSum, parameters=nothing; kwarg
44
end
55

66

7-
function propagate!(circuit, term_sum::TS, params=nothing; kwargs...) where TS<:AbstractTermSum
7+
function propagate!(circuit, term_sum::AbstractTermSum, params=nothing; kwargs...)
8+
89
prop_cache = propagate!(circuit, PropagationCache(term_sum), params; kwargs...)
9-
# we expect that there exists a constructor TS(prop_cache) for the back conversion
10-
# by default implemented for some storage types
11-
return TS(prop_cache)
10+
11+
# extracts the original input term sum
12+
return extractsum!(prop_cache, term_sum)
1213
end
1314

1415
"""

src/Base/propagationcache.jl

Lines changed: 87 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -9,19 +9,60 @@ abstract type AbstractPropagationCache end
99
## The interface to hook into with each library
1010
PropagationCache(thing::AbstractTermSum) = _thrownotimplemented(thing, :PropagationCache)
1111

12+
"""
13+
mainsum(prop_cache::AbstractPropagationCache)
14+
15+
Returns the current main term sum from the propagation cache.
16+
It may be over-allocated and filled with trash terms.
17+
Use `extractsum!(prop_cache)` to get a properly-sized and valid term sum.
18+
"""
1219
mainsum(prop_cache::AbstractPropagationCache) = _thrownotimplemented(prop_cache, :mainsum)
20+
21+
"""
22+
auxsum(prop_cache::AbstractPropagationCache)
23+
24+
Returns the current auxiliary term sum from the propagation cache.
25+
It may be over-allocated and filled with trash terms.
26+
"""
1327
auxsum(prop_cache::AbstractPropagationCache) = _thrownotimplemented(prop_cache, :auxsum)
1428

1529
setmainsum!(prop_cache::AbstractPropagationCache, new_mainsum) = _thrownotimplemented(prop_cache, :setmainsum!)
1630
setauxsum!(prop_cache::AbstractPropagationCache, new_auxsum) = _thrownotimplemented(prop_cache, :setauxsum!)
1731

32+
33+
# An optional interface for returning the mainsum when it is safe to return it as a whole or as a view.
34+
# Should leave the sum linked to the cache, and the cache unperturbed.
35+
# This is concrete type dependent.
36+
function activesum(prop_cache::AbstractPropagationCache)
37+
_thrownotimplemented(prop_cache, :activesum)
38+
end
39+
40+
"""
41+
swapsums!(prop_cache::AbstractPropagationCache)
42+
43+
Swaps the mainsum and auxsum pointers on the propagation cache.
44+
"""
1845
function swapsums!(prop_cache::AbstractPropagationCache)
1946
temp = mainsum(prop_cache)
2047
setmainsum!(prop_cache, auxsum(prop_cache))
2148
setauxsum!(prop_cache, temp)
2249
return prop_cache
2350
end
2451

52+
"""
53+
copyswapsums!(prop_cache::AbstractPropagationCache)
54+
55+
Copies the active contents of the mainsum into the auxsum and then calls swapsums!(prop_cache).
56+
This is useful for when the current auxsum is meant to carry the final result.
57+
"""
58+
function copyswapsums!(prop_cache::AbstractPropagationCache)
59+
# instead of just swapping auxsum(prop_cache) and mainsum(prop_cache),
60+
# we need to copy the mainsum into the aux sum and then swap the sums
61+
copy!(auxsum(prop_cache), mainsum(prop_cache))
62+
swapsums!(prop_cache)
63+
return prop_cache
64+
end
65+
2566
StorageType(prop_cache::AbstractPropagationCache) = StorageType(mainsum(prop_cache))
2667

2768
nsites(prop_cache::AbstractPropagationCache) = nsites(mainsum(prop_cache))
@@ -69,25 +110,62 @@ activeindices(prop_cache::AbstractPropagationCache) = view(indices(prop_cache),
69110
lastactiveindex(prop_cache::AbstractPropagationCache) = activeindices(prop_cache)[end]
70111

71112

113+
mult!(prop_cache::AbstractPropagationCache, scalar::Number) = mult!(mainsum(prop_cache), scalar)
72114

73115
function Base.resize!(prop_cache::AbstractPropagationCache, new_size::Int)
74116
_thrownotimplemented(prop_cache, :resize!)
75117
end
76118

77119
## Back-conversions
120+
121+
# effectively a out-of-place version of extractsum!()
78122
function (::Type{TS})(prop_cache::AbstractPropagationCache) where TS<:AbstractTermSum
79-
return convert(TS, _cachetosum!(StorageType(prop_cache), prop_cache))
123+
return convert(TS, extractsum!(deepcopy(prop_cache)))
124+
end
125+
126+
"""
127+
extractsum!(prop_cache::AbstractPropagationCache, which_sum::AbstractTermSum)
128+
129+
Extracts the indicated sum `which_sum` from the propagation cache.
130+
This resizes the cache to the active size and returns the indicated sum.
131+
Further manipulating prop_cache or the returned sum may invalidate the other.
132+
If the indicated sum is the auxsum, active contents will be copied over from mainsum.
133+
If neither `mainsum(prop_cache)` nor `auxsum(prop_cache)` is indicated, an error is thrown.
134+
"""
135+
function extractsum!(prop_cache::AbstractPropagationCache, which_sum::AbstractTermSum)
136+
if which_sum !== mainsum(prop_cache) && which_sum !== auxsum(prop_cache)
137+
throw(ArgumentError("Indicated sum is not part of the propagation cache."))
138+
end
139+
140+
# if the indicated sum is not the mainsum, it is the auxsum
141+
# copy contents over and extract
142+
if which_sum !== mainsum(prop_cache)
143+
copyswapsums!(prop_cache)
144+
end
145+
146+
return extractsum!(prop_cache)
80147
end
81148

82-
_cachetosum!(::DictStorage, prop_cache::AbstractPropagationCache) = mainsum(prop_cache)
149+
"""
150+
extractsum!(prop_cache::AbstractPropagationCache)
83151
84-
function _cachetosum!(::ArrayStorage, prop_cache::AbstractPropagationCache)
85-
# convert back to TermSum
86-
term_sum = mainsum(prop_cache)
87-
term_sum = resize!(term_sum, activesize(prop_cache))
88-
return term_sum
152+
Extracts the mainsum from the propagation cache.
153+
This resizes the cache to the active size and returns the mainsum.
154+
Further manipulating prop_cache or the returned sum may invalidate the other.
155+
"""
156+
function extractsum!(prop_cache::AbstractPropagationCache)
157+
return _extractsum!(StorageType(prop_cache), prop_cache)
89158
end
90159

91-
function _cachetosum!(::Type{ST}, ::PC) where {ST<:StorageType,PC<:AbstractPropagationCache}
92-
throw(ErrorException("cachetosum!(::$(ST), ::$(PC)) not implemented."))
160+
161+
_extractsum!(::DictStorage, prop_cache::AbstractPropagationCache) = mainsum(prop_cache)
162+
163+
function _extractsum!(::ArrayStorage, prop_cache::AbstractPropagationCache)
164+
# resize the entire cache to retain validity
165+
resize!(prop_cache, activesize(prop_cache))
166+
return mainsum(prop_cache)
93167
end
168+
169+
function _extractsum!(::Type{ST}, ::PC) where {ST<:StorageType,PC<:AbstractPropagationCache}
170+
throw(ErrorException("extractsum!(::$(ST), ::$(PC)) not implemented."))
171+
end

0 commit comments

Comments
 (0)