@@ -671,21 +671,13 @@ function get_coherence(ψ::QuantumObject{<:AbstractArray,KetQuantumObject})
671
671
if length (ψ. dims) == 1
672
672
return mapreduce (n -> sqrt (n - 1 ) * ψ. data[n] * conj (ψ. data[n- 1 ]), + , 2 : ψ. dims[1 ])
673
673
else
674
- R = CartesianIndices ((ψ. dims... ,))
675
- off = circshift (ψ. dims, 1 )
676
- off[end ] = 1
677
-
678
- x = sum (R) do j
679
- j_tuple = Tuple (j) .- 1
680
- if 0 in j_tuple
681
- return 0
682
- end
683
-
684
- J = dot (j_tuple, off) + 1
685
- J2 = dot (j_tuple .- 1 , off) + 1
686
- return prod (sqrt .(j_tuple)) * ψ[J] * conj (ψ[J2])
687
- end
674
+ off = sum (cumprod (reverse (ψ. dims[2 : end ]))) + 1
675
+ t = Tuple (reverse (ψ. dims))
688
676
677
+ x = 0.0im
678
+ for J in off+ 2 : length (ψ. data)
679
+ x += ψ[J] * conj (ψ[J- off]) * prod (sqrt .(_ind2sub (t, J) .- 1 ))
680
+ end
689
681
return x
690
682
end
691
683
end
@@ -694,25 +686,26 @@ function get_coherence(ρ::QuantumObject{<:AbstractArray,OperatorQuantumObject})
694
686
if length (ρ. dims) == 1
695
687
return mapreduce (n -> sqrt (n - 1 ) * ρ. data[n, n- 1 ], + , 2 : ρ. dims[1 ])
696
688
else
697
- R = CartesianIndices ((ρ. dims... ,))
698
- off = circshift (ρ. dims, 1 )
699
- off[end ] = 1
700
-
701
- x = sum (R) do j
702
- j_tuple = Tuple (j) .- 1
703
- if 0 in j_tuple
704
- return 0
705
- end
706
-
707
- J = dot (j_tuple, off) + 1
708
- J2 = dot (j_tuple .- 1 , off) + 1
709
- return prod (sqrt .(j_tuple)) * ρ[J, J2]
710
- end
689
+ off = sum (cumprod (reverse (ρ. dims[2 : end ]))) + 1
690
+ t = Tuple (reverse (ρ. dims))
711
691
692
+ x = 0.0im
693
+ for J in off+ 2 : length (ρ. data[1 , :])
694
+ x += ρ[J, J- off] * prod (sqrt .(_ind2sub (t, J) .- 1 ))
695
+ end
712
696
return x
713
697
end
714
698
end
715
699
700
+ function get_coherence (v:: QuantumObject{T,OperatorKetQuantumObject} ) where {T}
701
+ if length (v. dims) > 1
702
+ throw (ArgumentError (" Mean photon number not implemented for composite OPeratorKetQuantumObject" ))
703
+ end
704
+
705
+ d = v. dims[1 ]
706
+ return mapreduce (n -> sqrt (n - 1 ) * v. data[(n- 1 )* d+ n- 1 ], + , 2 : d)
707
+ end
708
+
716
709
@doc raw """
717
710
remove_coherence(ψ::QuantumObject)
718
711
@@ -739,42 +732,45 @@ Get the mean occupation number ``n`` by measuring the expectation value of the n
739
732
740
733
It returns the expectation value of the number operator.
741
734
"""
742
- function mean_occupation (ψ:: QuantumObject{T,KetQuantumObject} ) where {T}
743
- if length (ψ. dims) == 1
744
- return mapreduce (k -> abs2 (ψ[k]) * (k - 1 ), + , 1 : ρ. dims[1 ])
745
- else
746
- t = Tuple (ψ. dims)
735
+ function mean_occupation (ψ:: QuantumObject{T,KetQuantumObject} ; idx:: Union{Int,Nothing} = nothing ) where {T}
736
+ t = Tuple (reverse (ψ. dims))
737
+ mean_occ = zeros (length (ψ. dims))
747
738
748
- x = 0.0
749
- for J in eachindex (ψ. data)
750
- x += abs2 (ψ[J]) * prod (Base. _ind2sub (t, J) .- 1 )
751
- end
752
- return real (x)
739
+ for J in eachindex (ψ. data)
740
+ sub_indices = _ind2sub (t, J) .- 1
741
+ mean_occ .+ = abs2 (ψ[J]) .* sub_indices
753
742
end
743
+ reverse! (mean_occ)
744
+
745
+ return isnothing (idx) ? mean_occ : mean_occ[idx]
754
746
end
755
747
756
- function mean_occupation (ρ:: QuantumObject{T,OperatorQuantumObject} ) where {T}
757
- if length (ρ. dims) == 1
758
- return real (mapreduce (k -> ρ[k, k] * (k - 1 ), + , 1 : ρ. dims[1 ]))
759
- else
760
- t = Tuple (ρ. dims)
748
+ mean_occupation (ψ:: QuantumObject{T,KetQuantumObject,1} ) where {T} = mapreduce (k -> abs2 (ψ[k]) * (k - 1 ), + , 1 : ψ. dims[1 ])
761
749
762
- x = 0.0im
763
- for J in eachindex (ρ. data[:, 1 ])
764
- x += ρ[J, J] * prod (Base. _ind2sub (t, J) .- 1 )
765
- end
750
+ function mean_occupation (ρ:: QuantumObject{T,OperatorQuantumObject} ; idx:: Union{Int,Nothing} = nothing ) where {T}
751
+ t = Tuple (reverse (ρ. dims))
752
+ mean_occ = zeros (eltype (ρ. data), length (ρ. dims))
766
753
767
- return real (x)
754
+ x = 0.0im
755
+ for J in eachindex (ρ. data[:, 1 ])
756
+ sub_indices = _ind2sub (t, J) .- 1
757
+ mean_occ .+ = ρ[J, J] .* sub_indices
768
758
end
759
+ reverse! (mean_occ)
760
+
761
+ return isnothing (idx) ? real .(mean_occ) : real (mean_occ[idx])
769
762
end
770
763
771
- function mean_occupation (ρ:: QuantumObject{T,OperatorKetQuantumObject} ) where {T}
772
- if length (ρ. dims) > 1
764
+ mean_occupation (ρ:: QuantumObject{T,OperatorQuantumObject,1} ) where {T} =
765
+ mapreduce (k -> ρ[k, k] * (k - 1 ), + , 1 : ρ. dims[1 ])
766
+
767
+ function mean_occupation (v:: QuantumObject{T,OperatorKetQuantumObject} ) where {T}
768
+ if length (v. dims) > 1
773
769
throw (ArgumentError (" Mean photon number not implemented for composite OPeratorKetQuantumObject" ))
774
770
end
775
771
776
- d = ρ . dims[1 ]
777
- return real (mapreduce (k -> ρ [(k- 1 )* r + k] * (k - 1 ), + , 1 : d))
772
+ d = v . dims[1 ]
773
+ return real (mapreduce (k -> v [(k- 1 )* d + k] * (k - 1 ), + , 1 : d))
778
774
end
779
775
780
776
@doc raw """
0 commit comments