Full/CIPHI CI

ElemCo.FCIModule

FCI Module

This module contains a translation of the FCI C++ code of Gerald Knizia and extensions for selected CI and CIPHI (CIΦ - Selected CI via Perturbation, Heat-Bath and Iterations).

source

Store and Restart

CIPHI calculations can be stored and restarted using the wf.store and wf.start options. This is useful for:

  • Continuing a calculation with tighter thresholds
  • Computing PT2 corrections on a pre-converged determinant space
  • Multi-state calculations where states are stored separately

Storing CIPHI Calculations

@ciphi begin
  @set ciphi epsilon=1e-3 nstates=2
  @set wf store="my_ciphi.h5"
end

This stores the final determinants and CI coefficients to TREXIO files. For multi-state calculations, each state is stored in a separate file (e.g., my_ciphi.h5, my_ciphi_state2.h5).

Restarting from Stored Determinants

@ciphi begin
  @set ciphi epsilon=5e-4
  @set wf start="my_ciphi.h5"
end

The restart loads the stored determinants as the initial space and uses the stored CI coefficients as a warm start for the Davidson solver, significantly accelerating convergence.

PT2-Only Mode

To compute only the PT2 correction without additional variational iterations:

@ciphi begin
  @set ciphi pt2_only=true
  @set wf start="my_ciphi.h5"
end

This is useful when you have a converged determinant space and want to compute or recompute the PT2 correction with different parameters.

Exported functions

ElemCo.FCI.CIPHIContextType
CIPHIContext

Lightweight context for CIPHI (CIΦ - CI via Perturbative and Heat-Bath Iterative selection) calculations.

Unlike FCIContext, CIPHIContext does NOT pre-compute full-space address tables or diagonal Hamiltonian elements. Instead, it only stores the minimal data needed:

  • Integral data (FCIDump)
  • Calculation options (CIPHIOptions)
  • System size parameters
  • Modified core Hamiltonian (for correct diagonal element calculation)

Address tables and diagonal elements are computed on-demand only for the selected determinants during CIPHI iterations. This provides:

  • Faster initialization (no full-space addressing)
  • Lower memory usage (proportional to Nselected, not Ndeterminants)
  • Better scaling for large orbital spaces

Fields

  • fcidump::FCIDump - Integral data
  • options::CIPHIOptions - CIPHI-specific calculation options
  • n_orb::Int - Number of spatial orbitals
  • n_elec::Tuple{Int,Int} - (nalpha, nbeta) electron counts
  • reference_det::Determinant - Reference determinant
  • mod_core_h_a::Matrix{Scalar} - Modified core Hamiltonian for alpha spin
  • mod_core_h_b::Matrix{Scalar} - Modified core Hamiltonian for beta spin
  • heval_data::HEvalData - Precomputed arrays for diagonal and Fock elements
source
ElemCo.FCI.run_ciphi!Method
run_ciphi!(ctx::CIPHIContext; initial_dets=nothing, initial_coeffs=nothing) 
  -> (energies, coeffs, determinants, pt2_result)

Convenience method for CIPHIContext that uses bundled options.

This lightweight interface avoids FCIContext initialization overhead:

  • No full-space address tables computed upfront
  • No full-space diagonal H computed upfront
  • Initialization time proportional to Norbitals, not Ndeterminants

Keyword Arguments

  • initial_dets: Starting determinants from previous calculation (for restart)
  • initial_coeffs: Starting CI coefficients (optional, for warm start)

Returns

Same as runciphi!(ctx, options): (energies, coeffs, determinants, pt2result)

source
ElemCo.FCI.run_ciphi!Method
run_ciphi!(ctx::Union{FCIContext, CIPHIContext}, options::CIPHIOptions; 
                 initial_dets=nothing, initial_coeffs=nothing) 
  -> (Vector{Float64}, Matrix{Float64}, Vector{Determinant}, Vector{(Float64, Float64)})

Run CIPHI (CIΦ - Selected CI via Perturbation, Heat-Bath and Iterations) calculation with support for multiple states.

Arguments

  • ctx: FCI context
  • options: CIPHI options (including nstates for multi-state)

Keyword Arguments

  • initial_dets::Union{Nothing, Vector{<:AbstractDeterminant}}: Starting determinants from previous calculation
  • initial_coeffs::Union{Nothing, AbstractVecOrMat{Float64}}: Starting CI coefficients (optional, for warm start)

Returns

  • energies: Vector of length nstates with total energies (electronic + nuclear)
  • coefficients: Matrix (n_dets × nstates) with CI coefficients for all states
  • variational_dets: Vector of determinants in final variational space
  • pt2_result: PT2 correction results for all states

Notes

  • For nstates=1 (default), uses single-state selection strategy
  • For nstates>1, uses multi-state selection with state-maximum probability
  • If initial_dets is provided, these determinants are used as the starting variational space
source

Internal functions

ElemCo.FCI.CIPHISetupDataType
CIPHISetupData

Setup data: Pre-computed and sorted double excitation matrix elements.

For each pair of orbitals {p,q}, stores a list of triplets {r,s,|H(rs←pq)|}, sorted by |H| in decreasing order. This enables efficient generation of only important excitations during iterative selection.

Following Holmes et al. (2016), Algorithm Step IIa.

source
ElemCo.FCI.DeterminantType
Determinant

Represents a single determinant with alpha and beta orbital occupation patterns. Used for selected space determinant storage and manipulation.

source
ElemCo.FCI.DeterminantLookupIndexType
DeterminantLookupIndex{OPattern}

Fast lookup index for finding connected determinants in O(1) time.

Stores three dictionaries:

  • same_alpha: Maps alpha OPattern → Vector{Int} of determinant indices sharing that alpha
  • same_beta: Maps beta OPattern → Vector{Int} of determinant indices sharing that beta
  • singlexc_alpha: Maps alpha OPattern → Vector{OPattern} of alpha patterns connected by single excitation

This enables efficient lookup of candidates for:

  • Double-beta excitations (via same_alpha)
  • Double-alpha excitations (via same_beta)
  • Mixed alpha-beta excitations (via singlexcalpha then samealpha)

Reduces extendSelectedHamiltonianMatrix from O(N²) to O(N×Nconnections) where N_connections << N.

source
ElemCo.FCI.ExcValsType
ExcVals

Holds excitation values: coefficient and Hamiltonian matrix element required to calculate the contribution to the perturbative energy.

source
ElemCo.FCI.FCIVectorType
FCIVector{OPattern}

FCI vector storing coefficients as matrix M[iAdrA, iAdrB] where iAdrA and iAdrB are indices of orbital occupation strings for alpha/beta electrons.

source
ElemCo.FCI.HEvalDataType
HEvalData

Precomputed data for evaluating diagonal Hamiltonian and single excitations elements.

  1. The jkaa, jkbb, jab, ha, hb arrays store precomputed Coulomb and exchange contributions needed for efficient diagonal Hamiltonian element evaluation.

    • jkaa[i, j] = 0.5 * [(ii|jj) - (ij|ji)] for alpha spin
    • jkbb[i, j] = 0.5 * [(ii|jj) - (ij|ji)] for beta spin
    • jab[i, j] = (ii|jj) mixed alpha-beta
    • ha[i] = ⟨i|h|i⟩ for alpha spin
    • hb[i] = ⟨i|h|i⟩ for beta spin
  2. The h1e2 arrays contain combinations of two-electron integrals that appear frequently in single excitation matrix elements and Fock matrix construction. For example, for alpha-alpha excitations: h1e2[i, p, q] = v_{pi}^{qi} - v_{pi}^{iq} = (pq|ii) - (pi|iq)

    These arrays enable efficient computation of single excitation matrix elements via compute_fock_element.

source
ElemCo.FCI.HamiltonianTerm2eType
HamiltonianTerm2e <: HamiltonianTerm

Two-electron Hamiltonian term: $\[1/2\] (ij|kl) E^i_j E^k_l$

WARNING: Uses (ij|kl) integrals, NOT ⟨ij|kl⟩ and includes factor 1/2.

source
ElemCo.FCI.OrbSpacesMethod
OrbSpaces(n_orb::Int, buf::AbstractVector{Int}) -> OrbSpaces

Create OrbSpaces using provided buffer for occupied and virtual orbitals. Buffer size must be at least n_orb * 4.

source
ElemCo.FCI.OrbSpacesMethod
OrbSpaces(n_orb::Int) -> OrbSpaces

Create OrbSpaces with pre-allocated buffers for occupied and virtual orbitals.

source
ElemCo.FCI.OrbStringAdrTableType
OrbStringAdrTable{OPattern}

Auxiliary object for addressing orbital occupation patterns for one spin. Provides addressing of all patterns with a fixed total number of electrons in a given number of orbitals.

source
ElemCo.FCI.OrbStringAdrTableMethod
(table::OrbStringAdrTable{OPattern})(bit_string::OPattern) where OPattern -> Address

Get 1-based address for a given bit string pattern.

source
ElemCo.FCI.PSpaceDataType
PSpaceData

Container for P-space determinants, Hamiltonian matrix, and eigenvectors. Contains all data needed for P-space enhanced initial guess generation.

source
Base.copyMethod
Base.copy(vec::FCIVector{OPattern}) where OPattern -> FCIVector{OPattern}

Create a deep copy of an FCIVector, including all data.

source
Base.getindexMethod
Base.getindex(vec::FCIVector{OPattern}, i_a::Integer, i_b::Integer) where OPattern -> Scalar

Access coefficient vec[ia, ib].

source
Base.resize!Method
resize!(sel_ham::SelectedHamiltonianMatrix, dets::SelectedCIDeterminants, connections::Vector{Vector{Int}}, cursize)

Resize the SelectedHamiltonianMatrix to preallocate space for new elements.

source
Base.setindex!Method
Base.setindex!(vec::FCIVector{OPattern}, val::Scalar, i_a::Integer, i_b::Integer) where OPattern

Set coefficient vec[ia, ib] = val.

source
Base.zeroMethod
Base.zero(vec::FCIVector{OPattern}) where OPattern -> FCIVector{OPattern}

Create a zero FCIVector with the same dimensions.

source
ElemCo.FCI.absorb_1e!Method
absorb_1e!(int2::Array{Scalar, 4}, n_orb::Integer, n_elec::Integer, 
           core_h_x::Matrix{Scalar}, core_h_y::Matrix{Scalar})

Absorb one-electron operators into two-electron operator.

source
ElemCo.FCI.add!Method
add!(r::FCIVector{OPattern}, x::FCIVector{OPattern}, f::Scalar) where OPattern

Compute r += f * x using LinearAlgebra.

source
ElemCo.FCI.add_1rdm_for_spin!Method
add_1rdm_for_spin!(rdm::AbstractMatrix{Scalar}, coeff_l::AbstractVector{Scalar}, 
                  coeff_r::AbstractVector{Scalar}, adr1::OrbStringAdrTable, 
                  adr2::OrbStringAdrTable, st1::Integer, st2::Integer)

Add contribution to 1-RDM for one spin.

source
ElemCo.FCI.add_excitations!Method
add_excitations!(excitations::VecDict{Determinant, ExcVals}, det::Determinant, coef::Scalar,
                coef_dg::Union{Scalar, Nothing}, alpha_occ, beta_occ, n_orb, 
                pchb_excitations, fa, fb, ecorr, shift, epsilon::Float64, epsilon_c::Float64)

Generate mixed-spin double excitations from occupied alpha and beta orbitals using pre-computed Heat-Bath lists, adding only those with |H| > epsilon.

source
ElemCo.FCI.add_excitations!Method
add_excitations!(excitations::VecDict{Determinant, ExcVals}, det::Determinant,
                coef::Scalar, coef_dg::Union{Scalar, Nothing}, single_excitation_phase::Function, 
                occs, virts, occs_opp, int1, h1e2_same, h1e2_opp,
                fdiag, ecorr, shift, epsilon::Float64, epsilon_c::Float64)

Add single excitations to the excitations dictionary.

source
ElemCo.FCI.add_excitations!Method
add_excitations!(excitations::VecDict{Determinant, ExcVals}, det::Determinant,
                coef::Scalar, coef_dg::Union{Scalar, Nothing}, double_excitation_phase::Function,
                occ, pchb_excitations, fdiag, ecorr, shift, epsilon::Float64, epsilon_c::Float64)

Generate same-spin double excitations from occupied orbitals using pre-computed Heat-Bath lists, adding only those with |H| > epsilon and storing in excitations dictionary together with their weighted matrix elements.

source
ElemCo.FCI.add_strings_to_table_recursive!Method
add_strings_to_table_recursive!(table::OrbStringAdrTable{OPattern}, old_pat::OPattern, 
                               n_elec_left::Integer, i_first_orb::Integer) where OPattern

Recursively add patterns with nelecleft electrons in the remaining orbitals.

source
ElemCo.FCI.apply_1e_op!Method
apply_1e_op!(result::AbstractVector{Scalar}, coeffs::AbstractVector{Scalar}, 
            prefactor::Scalar, op_matrix_1e::AbstractMatrix{Scalar},
            adr1::OrbStringAdrTable, adr2::OrbStringAdrTable,
            st1::Integer, st2::Integer)

Apply 1-electron operator on specified spin branch.

source
ElemCo.FCI.apply_cop1Method
apply_cop1(input_pattern::OPattern, iorb::Integer, create_or_destroy::Integer) where OPattern -> Tuple{OPattern, Int8}

Apply orbital creation (+1) or destruction (-1) operator on a determinant string. Returns (output_pattern, sign) where:

  • sign = +1: operation has positive parity
  • sign = -1: operation has negative parity
  • sign = 0: operation annihilates input
source
ElemCo.FCI.block_contract_cc1!Method
block_contract_cc1!(data_k::AbstractArray{Scalar, 3}, info1::Vector{StrInfo},
                    coeffs::AbstractMatrix{Scalar},
                    direction::Char, c_sum::Ref{Scalar}, prefactor::Scalar)

Block contraction for c^k c_l operators. Direction: 'c' for contraction, 'R' for residual formation.

source
ElemCo.FCI.block_contract_cc1_nosym!Method
block_contract_cc1_nosym!(data_k, info_1, coeffs, c_sum, prefactor)

Helper function for 2-RDM calculation. Performs block contraction for non-symmetric pairs.

Forms: data_k[k,l,iBlk1,iBlk2] += <K_1|c†_k c_l|J_1> * coeffs[J_1,K_2] * sign * prefactor

Arguments

  • data_k: Output array [norb, norb, nblk1, nblk2]
  • info_1: Array of StrInfo for spin 1 substitutions
  • coeffs: CI coefficients as AbstractMatrix [n_str_1, n_blk_2] (can be StridedView)
  • c_sum: Accumulator for sum of contributions (for screening)
  • prefactor: Multiplicative prefactor (typically ±1)
source
ElemCo.FCI.build_lookup_index!Method
build_lookup_index!(index::DeterminantLookupIndex{OPattern}, determinants::Vector{Determinant{OPattern}}, 
                   start_idx::Int, end_idx::Int, verbosity::Int) where OPattern

Build samealpha, samebeta and singleexcalpha index dictionaries for determinants in range [startidx:endidx]. samealpha/beta: Appends determinant indices to vectors for each unique alpha/beta pattern. singleexc_alpha: Maps alpha patterns to vectors of connected alpha patterns via single excitations.

source
ElemCo.FCI.build_pspace_hamiltonian!Method
build_pspace_hamiltonian!(context::FCIContext)

Build the P-space Hamiltonian matrix using efficient Selected CI machinery. This replaces the slow full-space approach with fast selected-space operations.

source
ElemCo.FCI.build_small_space_hamiltonianMethod
build_small_space_hamiltonian(context::Union{FCIContext, CIPHIContext}, determinants::Vector{Determinant}) -> Matrix{Scalar}

Build Hamiltonian matrix for small space of determinants. Uses Selected CI framework for efficient matrix element computation.

Arguments

  • context: FCI or CIPHIContext
  • determinants: Vector of determinants spanning the small space

Returns

  • Hamiltonian matrix H[i,j] = ⟨deti|H|detj⟩
source
ElemCo.FCI.calc_diagonalHMethod
calc_diagonalH(hed::HEvalData, occa::AbstractVector{Int}, occb::AbstractVector{Int}) -> Scalar

Evaluate diagonal Hamiltonian element ⟨Ψ|H|Ψ⟩ for determinant |occa, occb⟩.

source
ElemCo.FCI.calc_fock_diagonal4det!Method
calc_fock_diagonal4det!(fock::FockDiagonal, ctx::Union{FCIContext, CIPHIContext}, occa, occb)

Compute diagonal of the Fock matrix for a given determinant defined by occupied orbitals occa and occb.

fock is modified in-place and returned.

source
ElemCo.FCI.calc_mod_core_h!Method
calc_mod_core_h!(mod_core_h::Matrix{Scalar}, int2::Array{Scalar, 4}, n_orb::Integer, c1_integrals::Bool)

Calculate modified core Hamiltonian by absorbing two-electron contributions arising from changed order of creation/annihilation operators.

source
ElemCo.FCI.calculate_double_excitation_phaseMethod
calculate_double_excitation_phase(pattern::OPattern, orb_i::Int, orb_j::Int, orb_a::Int, orb_b::Int) where OPattern -> Int

Calculate phase factor for double excitation ij -> ab.

The phase is calculated by decomposing into two successive single excitations:

  1. First excitation: i -> a, with phase φ₁
  2. Second excitation: j -> b in modified determinant, with phase φ₂

Total phase = φ₁ × φ₂

This approach correctly handles the fermionic anticommutation relations.

source
ElemCo.FCI.compatibleMethod
compatible(a::FCIVector{OPattern}, b::FCIVector{OPattern}) where OPattern -> Bool

Check if two FCI vectors are compatible for operations.

source
ElemCo.FCI.compute_diagonal_elementMethod
compute_diagonal_element(occa::AbstractVector{Int}, occb::AbstractVector{Int}, ctx) -> Scalar

Compute diagonal matrix element ⟨det|H|det⟩ for a single determinant using HEvalData. Works with both FCIContext and CIPHIContext.

source
ElemCo.FCI.compute_diagonal_elementMethod
compute_diagonal_element(det::Determinant, ctx) -> Scalar

Compute diagonal matrix element ⟨det|H|det⟩ for a single determinant using HEvalData. Works with both FCIContext and CIPHIContext.

source
ElemCo.FCI.compute_fock_elementMethod
compute_fock_element(int1, h1e2_same, h1e2_opp, occ_same::AbstractVector, occ_opp::AbstractVector,
                    a::Int, i::Int) -> Float64

Compute Fock matrix element fai fai = hai + Σj (vaijj - vajji)SS + Σj (vaijj)OS where SS = same spin, OS = opposite spin.

source
ElemCo.FCI.compute_fock_elementMethod
compute_fock_element(int1, h1e2_same, h1e2_opp, str_same::OPattern, str_opp::OPattern,
                    a::Int, i::Int) where OPattern -> Float64

Compute Fock matrix element fai fai = hai + Σj (vaijj - vajji)SS + Σj (vaijj)OS where SS = same spin, OS = opposite spin.

source
ElemCo.FCI.compute_matrix_element_directFunction
compute_matrix_element_direct(det_i::Determinant, det_j::Determinant, 
                             context, occa=nothing, occb=nothing) -> Scalar

Compute ⟨detj|Ĥ|deti⟩ directly using orbital excitation analysis. Works with both FCIContext and CIPHIContext.

occa/occb are either Nothing or lists of occupied orbitals (makes the calculation more efficient).

source
ElemCo.FCI.compute_pt2_correction!Method
compute_pt2_correction!(selected_ctx, coefficients, E_var, setup_data, options)

Compute second-order perturbative correction to variational energy.

Following Holmes et al. (2016), Section III.B: ΔE = ∑k [ (∑i Hki ci)² / (E⁽⁰⁾ - H_kk) ]

where k runs over external determinants (not in variational space) and i runs over internal determinants (in variational space).

Returns PT2 energies as a vector.

source
ElemCo.FCI.contract!Function
contract!(term::HamiltonianTerm, r::FCIVector, c::FCIVector, prefactor::Scalar)

Apply Hamiltonian term: |r⟩ += prefactor * H |c⟩

source
ElemCo.FCI.contract!Method
contract!(term::HamiltonianTerm1e, r::FCIVector, c::FCIVector, prefactor::Scalar)

Apply one-electron Hamiltonian term.

source
ElemCo.FCI.contract!Method
contract!(term::HamiltonianTerm2e, r::FCIVector, c::FCIVector, prefactor::Scalar)

Apply two-electron Hamiltonian term.

source
ElemCo.FCI.contract_hamiltonian!Method
contract_hamiltonian!(context::FCIContext, r::FCIVector, c::FCIVector, prefactor::Scalar)

Apply full Hamiltonian: |r⟩ += prefactor * H |c⟩

source
ElemCo.FCI.contract_hamiltonian!Method
contract_hamiltonian!(selected_ctx::SelectedCIContext, result::Vector{Scalar}, 
                     input::Vector{Scalar}, prefactor::Scalar)

Interface to existing Davidson solver infrastructure for Selected CI.

source
ElemCo.FCI.contract_hamiltonian_selected!Method
contract_hamiltonian_selected!(result::Vector{Scalar}, input::Vector{Scalar}, 
                              selected_ctx::SelectedCIContext, prefactor::Scalar)

Compute H*c matrix-vector product using precomputed Hamiltonian elements.

source
ElemCo.FCI.count_excitation_levelMethod
count_excitation_level(det1::Determinant, det2::Determinant) -> Int

Count the excitation level between two determinants. Returns the number of orbital differences (alpha + beta).

source
ElemCo.FCI.davidson_fci!Method
davidson_fci!(context::FCIContext, n_states::Union{Int, Nothing} = nothing) 
-> Tuple{Vector{Scalar}, Vector{FCIVector}}

Unified Davidson diagonalization for FCI with subspace refresh capability. Always returns arrays of energies and states for type stability.

Arguments

  • context: FCI context containing system information
  • n_states: Number of electronic states to compute (default: uses context.options.nstates)

Returns

  • Tuple{Vector{Scalar}, Vector{FCIVector}}: Arrays of energies and corresponding eigenvectors
source
ElemCo.FCI.davidson_selected_ci!Method
davidson_selected_ci!(selected_ctx, initial_guesses; kwargs...)

Davidson diagonalization in selected CI space.

This is a specialized Davidson algorithm for selected CI calculations where the Hamiltonian matrix elements are computed on-the-fly. It uses the same Davidson algorithm as davidson_fci! but operates on a selected subset of determinants rather than the full CI space.

Automatically detects whether the Hamiltonian is Hermitian or non-Hermitian based on the context (similarity-transformed integrals are non-Hermitian).

Arguments

  • selected_ctx::SelectedCIContext: Selected CI context containing determinants
  • initial_guesses::Matrix{Scalar}: Initial guess vector in selected CI basis (nselected × nguess)

Keyword Arguments

  • nstates::Int=1: Number of lowest eigenvalues to compute
  • max_iterations::Int=50: Maximum number of Davidson iterations
  • convergence_threshold::Float64=1e-8: Energy convergence threshold
  • shift::Float64=0.1: (square of imaginary) level shift for preconditioner
  • max_subspace::Int=30: Maximum subspace size before refresh
  • verbose::Bool=false: Print iteration information

Returns

  • Tuple{Vector{Float64}, Matrix{Float64}}: Eigenvalues and eigenvectors
    • eigenvalues: Vector of lowest nstates eigenvalues
    • eigenvectors: Matrix of eigenvectors (n_selected × nstates(times 2 for non-Hermitian))

Algorithm

Uses the Davidson iterative diagonalization method:

  1. Build subspace by expanding with correction vectors
  2. Project Hamiltonian onto subspace
  3. Diagonalize small projected Hamiltonian (Hermitian or non-Hermitian)
  4. Compute residuals and check convergence
  5. Add correction vectors to expand subspace
  6. Refresh subspace when it becomes too large

For non-Hermitian Hamiltonians (similarity-transformed integrals):

  • Uses standard eigen() instead of eigen(Hermitian())
  • Preconditioner uses complex shift to handle non-real eigenvalues
  • The left eigenvectors are returned in the same array as right eigenvectors (after the right ones)

The key difference from davidson_fci! is that matrix elements are computed on-the-fly using contract_hamiltonian_selected!, maintaining O(Nselected) memory usage rather than O(Nfull).

source
ElemCo.FCI.determinant_from_addressMethod
determinant_from_address(context::FCIContext, addr::Address) -> Determinant

Convert a determinant address to alpha/beta orbital patterns. Uses the addressing tables to reconstruct the determinant.

source
ElemCo.FCI.diagonal_matrix_elementMethod
diagonal_matrix_element(det::Determinant, context) -> Scalar

Compute diagonal matrix element ⟨det|Ĥ|det⟩. For FCIContext uses precomputed diagonal, for CIPHIContext computes on-the-fly.

source
ElemCo.FCI.diagonalize_selected_spaceMethod
diagonalize_selected_space(selected_ctx::SelectedCIContext; 
                           nstates::Int=1,
                           previous_vectors::Union{Nothing,Matrix{Float64}}=nothing,
                           conv_tol::Float64=1e-6) 
  -> (Vector{Float64}, Matrix{Float64})

Diagonalize the Hamiltonian in the selected CI space. Returns eigenvalues and eigenvectors for nstates lowest states.

For small spaces (< 1000 determinants), uses direct diagonalization via eigen(). For large spaces (≥ 1000 determinants), uses Davidson iterative diagonalization.

Arguments

  • selected_ctx: Selected CI context with determinants
  • nstates: Number of lowest eigenstates to compute (default: 1)
  • previous_vectors: Optional previous eigenvectors to use as initial guess for Davidson. Should be a matrix of size (nprev, nstates) where nprev is the number of determinants in the previous iteration. Will be projected onto the current determinant space.

Returns

  • eigenvalues: Vector of length nstates with lowest eigenvalues
  • eigenvectors: Matrix of size (n_selected, nstates) with eigenvectors
  • For non-Hermitian Hamiltonians (similarity-transformed integrals), both right and left eigenvectors are computed and returned in the same matrix (right vectors first, then left).
source
ElemCo.FCI.double_alpha_beta_excitation_phaseMethod
double_alpha_beta_excitation_phase(det::Determinant, orb_i_alpha::Int, orb_i_beta::Int,
                                   orb_a_alpha::Int, orb_a_beta::Int) -> (Determinant, Int)

Calculate phase factor for double alpha-beta excitation iα jβ -> aα bβ.

source
ElemCo.FCI.double_alpha_excitation_phaseMethod
double_alpha_excitation_phase(det::Determinant, orb_i::Int, orb_j::Int, orb_a::Int, orb_b::Int) -> (Determinant, Int)

Create determinant and calculate phase factor for double alpha excitation ij -> ab.

source
ElemCo.FCI.double_beta_excitation_phaseMethod
double_beta_excitation_phase(det::Determinant, orb_i::Int, orb_j::Int, orb_a::Int, orb_b::Int) -> (Determinant, Int)

Create determinant and calculate phase factor for double beta excitation ij -> ab.

source
ElemCo.FCI.double_excitation_alphaMethod
double_excitation_alpha(det::Determinant{OPattern}, i::Int, j::Int, a::Int, b::Int) where OPattern -> Determinant{OPattern}

Create determinant with alpha electrons moved from orbitals i,j to orbitals a,b.

source
ElemCo.FCI.double_excitation_betaMethod
double_excitation_beta(det::Determinant{OPattern}, i::Int, j::Int, a::Int, b::Int) where OPattern -> Determinant{OPattern}

Create determinant with beta electrons moved from orbitals i,j to orbitals a,b.

source
ElemCo.FCI.double_excitation_mixedMethod
double_excitation_mixed(det::Determinant, i_alpha::Int, i_beta::Int, a_alpha::Int, a_beta::Int) -> Determinant

Create determinant with one alpha excitation ialpha->aalpha and one beta excitation ibeta->abeta.

source
ElemCo.FCI.extend!Method
extend!(selected_ctx::SelectedCIContext, new_dets::Vector{Determinant})

Extend the SelectedCIContext with new determinants.

source
ElemCo.FCI.extend!Method
extend!(dets::SelectedCIDeterminants, new_dets::Vector{Determinant}, new_addresses::Vector{Address})

Extend SelectedCIDeterminants with new determinants and addresses. Incrementally updates the lookup index for efficient connected determinant queries.

source
ElemCo.FCI.extend!Method
extend!(sel_ham::SelectedHamiltonianMatrix, dets::SelectedCIDeterminants, context)

Extend the SelectedHamiltonianMatrix to include new determinants. Uses fast lookup index to find connected determinants in O(N×N_connections) instead of O(N²).

source
ElemCo.FCI.extract_full_to_selected!Method
extract_full_to_selected!(v_selected::Vector{Scalar}, v_full::FCIVector, 
                         selected_ctx::SelectedCIContext)

Extract selected CI coefficients from full CI vector.

source
ElemCo.FCI.find_excitation_orbitalsMethod
find_excitation_orbitals(pattern_i::OPattern, pattern_j::OPattern) where OPattern -> (Int, Int)

Find the two orbitals involved in a single excitation i -> a.

source
ElemCo.FCI.fmt_detMethod
fmt_det(pat_a::OPattern, pat_b::OPattern, n_max_orb::Integer) where OPattern -> String

Format determinant (alpha and beta patterns) as string.

source
ElemCo.FCI.fmt_patMethod
fmt_pat(pat::OPattern, n_max_orb::Integer) where OPattern -> String

Format orbital pattern as string.

source
ElemCo.FCI.form_string_substs_for_spin!Method
form_string_substs_for_spin!(result::Vector{SubstResult{OPattern}}, 
                            op_matrix_1e, adr::OrbStringAdrTable{OPattern},
                            I::OPattern, ThrNeglect=1e-16) where OPattern -> Int

Form sparse list of all |K> which can be reached by applying c^k_l on string |I>.

Returns number of valid substitutions found.

source
ElemCo.FCI.generate_excitations!Method
generate_excitations!(excitations::VecDict{Determinant, ExcVals},
                      det::Determinant, coef::Scalar, 
                      coef_dg::Union{Scalar, Nothing}, ecorr::Scalar,
                      ctx::FCIContext,
                      setup_data::CIPHISetupData, spaces::OrbSpaces, fockd::FockDiagonal,
                      epsilon::Float64, shift) -> Int

Generate only excitations with |H| > epsilon using pre-computed data.

This is the efficient excitation generation from Holmes et al. (2016):

  1. For doubles: Use pre-sorted lists to stop early when |H| < epsilon
  2. For singles: Compute on-the-fly and discard if |H| < epsilon

Additionally, H*coef/denom and coef*H is computed and stored during generation for efficiency.

Works with both FCIContext and CIPHIContext.

spaces is an OrbSpaces object used for temporary storage of occupied and virtual orbitals. fockd is the Fock diagonal object used to store Fock matrix diagonals for the determinant. coef_dg is the bra coefficient of the determinant (dagger) if needed, otherwise nothing.

source
ElemCo.FCI.generate_pspace_initial_guess!Method
generate_pspace_initial_guess!(context::FCIContext, guess_vectors::Vector{FCIVector},
                              n_states::Int)

Generate high-quality initial guess vectors using P-space eigenvectors. This replaces the diagonal-based initial guess with P-space enhanced vectors.

source
ElemCo.FCI.get_connectionsMethod
get_connections(index::DeterminantLookupIndex, determinants::Vector{Determinant}, 
                start_idx::Int, end_idx::Int) -> Vector{Vector{Int}}

Get connected determinants for each determinant in range [startidx:endidx]

source
ElemCo.FCI.get_diagonal_elementMethod
get_diagonal_element(selected_ctx::SelectedCIContext, idet::Int) -> Scalar

Get diagonal Hamiltonian element for selected determinant index.

source
ElemCo.FCI.get_diagonal_elementMethod
get_diagonal_element(sel_ham::SelectedHamiltonianMatrix, idet::Int) -> Scalar

Get diagonal Hamiltonian element for selected determinant index.

source
ElemCo.FCI.get_reference_determinantMethod
get_reference_determinant(context::Union{FCIContext, CIPHIContext}) -> Determinant

Return the reference determinant. This is used as the starting point for P-space determinant selection.

source
ElemCo.FCI.hamiltonian_matrixMethod
hamiltonian_matrix(selected_ctx::SelectedCIContext) -> Matrix{Scalar}

Construct full Hamiltonian matrix for selected determinants.

source
ElemCo.FCI.heatbath_selectionFunction
heatbath_selection(selected_ctx::SelectedCIContext,
                   variational_coeffs::AbstractVector{Scalar},
                   options::CIPHIOptions,
                   E_current::Float64,
                   setup_data::CIPHISetupData,
                   detorder::Union{Nothing, Vector{Int}}=nothing, store_dets::Bool=true) 
                   -> (VecDict{Determinant, Scalar}, (Float64, Float64))

Select determinants using Heat-Bath preselection + perturbative selection. Uses efficient excitation generation with threshold-based filtering. Works with both FCIContext and CIPHIContext.

Returns selected determinants together with the weights and PT2 energy correction. If store_dets is false, only the PT2 energy is returned (with empty determinant list).

source
ElemCo.FCI.init!Method
init!(table::OrbStringAdrTable{OPattern}, n_elec::Integer, n_orb::Integer) where OPattern

Initialize the orbital string addressing table.

source
ElemCo.FCI.initialize_multistate_from_small_spaceMethod
initialize_multistate_from_small_space(context::Union{FCIContext, CIPHIContext}, target_selection::Int, nstates::Int) -> SmallSpaceResult

Initialize multi-state CIPHI using small-space Hamiltonian diagonalization. This provides better initial guesses for all states, preventing missed excited states.

Algorithm

  1. Select small space: max(100, sqrt(target_selection), 5*nstates) determinants
  2. Build Hamiltonian in small space
  3. Diagonalize to get nstates lowest eigenstates
  4. Return determinants and eigenvectors as initial guess for CIPHI

Arguments

  • context: FCI or CIPHI context
  • target_selection: Target CIPHI variational space size (for adaptive sizing)
  • nstates: Number of states to compute

Returns

  • SmallSpaceResult containing determinants, eigenvalues, and eigenvectors
source
ElemCo.FCI.inject_pspace_to_full!Method
inject_pspace_to_full!(c::FCIVector, c_pspace::Vector{Scalar}, 
                      pspace_data::PSpaceData)

Map P-space correction vector back to full CI space. Sets coefficients at P-space determinant positions.

source
ElemCo.FCI.jacobi_davidson_correction!Method
jacobi_davidson_correction!(t::FCIVector, r::FCIVector, u::FCIVector,
                           theta::Scalar, context::FCIContext, shift::Scalar)

Compute Jacobi-Davidson correction vector using P-space enhanced preconditioning: (I - uu^T) * (H - θI) * (I - u*u^T) * t = -r

This solves the projected correction equation to ensure the result is orthogonal to the current approximate eigenvector u, preventing linear dependency in the Davidson subspace.

Algorithm:

  1. Project residual to ensure orthogonality: r_proj = (I - u*u^T) * r
  2. If P-space available:
    • Extract P-space components of r_proj and u
    • Solve projected P-space system with double projection
    • Inject P-space correction into full space
    • Apply projected Davidson-Jacobi to Q-space
  3. Otherwise:
    • Apply projected Davidson-Jacobi to all determinants
  4. Final projection to enforce orthogonality

Arguments:

  • t: Output correction vector (modified in-place)
  • r: Residual vector
  • u: Current Ritz vector (approximate eigenvector, should be normalized)
  • theta: Current Ritz value (approximate eigenvalue)
  • context: FCI context with Hamiltonian and P-space data
  • shift: Level shift for regularization

Result: t is orthogonal to u by construction (dot(t, u) ≈ 0)

source
ElemCo.FCI.make_1rdms!Method
make_1rdms!(rdm_a::Matrix{Scalar}, rdm_b::Matrix{Scalar},
            coeff_l::FCIVector, coeff_r::FCIVector)

Compute 1-RDMs for alpha and beta spins as transition density matrices.

Computes:

  • Γα[r,s] = <coeffl|c†{rα} c{sα}|coeff_r>
  • Γβ[r,s] = <coeffl|c†{rβ} c{sβ}|coeff_r>

For a single state (coeffl == coeffr), this gives the regular 1-RDM. For different states, this gives the transition density matrix.

Arguments

  • rdm_a: Pre-allocated norb × norb matrix for alpha 1-RDM
  • rdm_b: Pre-allocated norb × norb matrix for beta 1-RDM
  • coeff_l: Left FCI vector (bra state)
  • coeff_r: Right FCI vector (ket state)
source
ElemCo.FCI.make_1rdms!Method
make_1rdms!(rdm_a::Matrix{Scalar}, rdm_b::Matrix{Scalar}, coeff::FCIVector)

Convenience method for computing 1-RDM of a single state (self-transition).

source
ElemCo.FCI.make_2rdm!Method
make_2rdm!(rdm2::Array{Scalar, 4}, coeff::FCIVector, rdm1::Matrix{Scalar}, ThrNeglect=1e-16)

Compute 2-particle reduced density matrix (2-RDM).

Computes: Γ[r,s,t,u] = <coeff|e^{rs}_{tu}|coef> = <coef| E^r_t E^s_u - \delta_t^s E^r_u |coeff> where E^r_s = c†_r c_s is the singlet excitation operator.

The algorithm:

  1. Loop over blocks of alpha/beta strings
  2. Form intermediate matrices: Inp[kl,K] = <K|c†_k c_l|J> c[J,K]
  3. Contract to 2-RDM (E^rt E^su): R[tr,su] += Inp[tr,K] * Inp[su,K]
  4. Permute and subtract to get final 2-RDM: Γ[r,s,t,u] = R[t,r,s,u] - RDM1[r,u] * δ_t^s

Arguments

  • rdm2: Pre-allocated 4D array [norb, norb, norb, norb]
  • coeff: FCI vector

Notes

  • Computational cost: O(Ndet × norb^4)
source
ElemCo.FCI.make_diagonal_h!Method
make_diagonal_h!(context::FCIContext, diag_h::FCIVector)

Compute diagonal Hamiltonian matrix elements using precomputed heval_data.

source
ElemCo.FCI.make_patternMethod
make_pattern(table::OrbStringAdrTable{OPattern}, adr::Address) where OPattern -> OPattern

Create orbital pattern from address.

source
ElemCo.FCI.modify_excitation!Method
modify_excitation!(excitations::Dict{Determinant, ExcVals},
                   det::Determinant, vals::ExcVals) -> Float64

Modify existing excitation entry in the excitations dictionary by adding new ExcVals. If the determinant is not present, returns the energy contribution from the new ExcVals.

source
ElemCo.FCI.n_dataMethod
n_data(vec::FCIVector{OPattern}) where OPattern -> Int

Total number of data elements.

source
ElemCo.FCI.n_old_detsMethod
n_old_dets(selci::SelectedCIContext) -> Int

Get the number of determinants in the previous iteration.

source
ElemCo.FCI.n_spinMethod
n_spin(vec::FCIVector{OPattern}) where OPattern -> FCIUInt

Total spin quantum number.

source
ElemCo.FCI.noccupiedMethod
noccupied(pattern::OPattern) where OPattern -> Int

Count number of occupied orbitals in the given orbital pattern.

source
ElemCo.FCI.orthogonalize_against!Method
orthogonalize_against!(v::Vector{Scalar}, u::Vector{Scalar})

Vector version for P-space operations. Remove component of v parallel to u: v = v - (u' * v) * u Assumes u is normalized. Modifies v in-place.

source
ElemCo.FCI.orthogonalize_against!Method
orthogonalize_against!(v::FCIVector{OPattern}, u::FCIVector{OPattern}) where OPattern

Remove component of v parallel to u: v = v - (u' * v) * u Assumes u is normalized. Modifies v in-place. This is the projection operator: (I - u*u^T) * v

source
ElemCo.FCI.project_pspace_to_fullspace!Method
project_pspace_to_fullspace!(v_full::FCIVector, v_pspace::Vector{Scalar}, 
                             pspace_data::PSpaceData)

Project P-space eigenvector onto full CI space. Zeros coefficients for determinants not in P-space and normalizes.

source
ElemCo.FCI.project_to_pspaceMethod
project_to_pspace(r::FCIVector, pspace_data::PSpaceData) -> Vector{Scalar}

Extract P-space components from full CI vector. Returns a vector of size n_pspace containing the coefficients at P-space determinants.

source
ElemCo.FCI.refresh_davidson_subspace!Method
refresh_davidson_subspace!(V, HV, eigenvecs, k::Int, n_keep::Int)

Refresh Davidson subspace by keeping the most important eigenvectors. This is called when the subspace becomes too large.

Arguments

  • V: Array of subspace vectors
  • HV: Array of Hamiltonian-vector products
  • eigenvecs: Current eigenvectors
  • k: Current subspace size
  • n_keep: Number of vectors to keep after refresh

Returns

  • New subspace size after refresh
source
ElemCo.FCI.select_pspace_determinants!Method
select_pspace_determinants!(context::FCIContext)

Select P-space determinants based on the configured selection method. Populates context.pspace_data with selected determinants and their indices.

source
ElemCo.FCI.select_small_space_determinantsMethod
select_small_space_determinants(context::CIPHIContext, target_size::Int, nstates::Int=1) -> Vector{Determinant}

Select determinants for small-space Hamiltonian diagonalization. For CIPHIContext, generates determinants by excitation level from reference, then calculates diagonal energies only for the generated determinants.

Arguments

  • context: CIPHI context
  • target_size: Target number of determinants (adaptive: max(100, sqrt(target_selection), 5*nstates))
  • nstates: Number of states to compute (used for sizing)

Returns

  • Vector of selected determinants
source
ElemCo.FCI.select_small_space_determinantsMethod
select_small_space_determinants(context::FCIContext, target_size::Int, nstates::Int=1) -> Vector{Determinant}

Select determinants for small-space Hamiltonian diagonalization. Uses the same hybrid selection method as traditional P-space.

Arguments

  • context: FCI context
  • target_size: Target number of determinants (adaptive: max(100, sqrt(target_selection), 5*nstates))
  • nstates: Number of states to compute (used for sizing)

Returns

  • Vector of selected determinants
source
ElemCo.FCI.set_occupied_orbspaces!Method
set_occupied_orbspaces!(orbspaces::OrbSpaces, det::Determinant)

Set occupied orbital indices in orbspaces based on the given det.

The occa, and occb fields of orbspaces have to be pre-allocated with sufficient size (at least norb).

source
ElemCo.FCI.set_orbspaces!Method
set_orbspaces!(orbspaces::OrbSpaces, det::Determinant)

Set occupied and virtual orbital indices in orbspaces based on the given det.

The occa, virta, occb, and virtb fields of orbspaces have to be pre-allocated with sufficient size (at least norb).

source
ElemCo.FCI.setup_ciphi!Method
setup_ciphi!(ctx::Union{FCIContext, CIPHIContext}) -> CIPHISetupData

Setup: Pre-compute and store sorted double excitation matrix elements.

For each pair of orbitals {p,q}, computes H(rs ← pq) for all distinct {r,s} pairs that don't include {p,q}, and stores them sorted by |H| in decreasing order.

This enables efficient generation of only important excitations, avoiding computation of matrix elements that would be below threshold.

Algorithm from Holmes et al. (2016), IIa:

  • Time complexity: O(M^4 log M)
  • Space complexity: O(M^4)

where M is the number of orbitals.

source
ElemCo.FCI.setup_ciphi_rhf!Method
setup_ciphi_rhf!(ctx::Union{FCIContext, CIPHIContext}) -> CIPHISetupData

Setup for RHF systems using spatial orbital integrals.

source
ElemCo.FCI.setup_ciphi_uhf!Method
setup_ciphi_uhf!(ctx::Union{FCIContext, CIPHIContext}) -> CIPHISetupData

Setup for UHF systems using spin-separated integrals. Handles three types of double excitations:

  • Alpha-alpha (using int2aa)
  • Beta-beta (using int2bb)
  • Mixed alpha-beta (using int2ab)
source
ElemCo.FCI.setup_pspace!Function
setup_pspace!(context::FCIContext, n_states::Int=1)

Complete P-space setup: select determinants, build Hamiltonian, and diagonalize. This is the main entry point for P-space initialization.

Supports two modes:

  1. Traditional: Excitation-based or energy-based determinant selection
  2. HBCI: Uses Heat-Bath CI to select important determinants (more efficient)

Arguments

  • context: FCI context
  • n_states: Number of states to compute in subsequent Davidson (for CIPHI multi-state P-space)
source
ElemCo.FCI.setup_pspace_ciphi!Function
setup_pspace_ciphi!(context::FCIContext, n_states::Int=1)

Use CIPHI to select P-space determinants. This provides a more efficient and targeted selection compared to traditional methods.

The selected determinants from CIPHI variational space become the P-space for subsequent full FCI Davidson iterations.

Arguments

  • context: FCI context
  • n_states: Number of states to compute (CIPHI will compute the same number of roots)
source
ElemCo.FCI.setup_selected_ci_from_determinants!Function
setup_selected_ci_from_determinants!(context::Union{FCIContext, CIPHIContext}, determinants::Vector{Determinant}, hamiltonian=SelectedHamiltonianMatrix()) -> SelectedCIContext

Create SelectedCIContext from list of determinants.

source
ElemCo.FCI.single_alpha_excitation_phaseMethod
single_alpha_excitation_phase(det::Determinant, orb_i::Int, orb_a::Int) -> (Determinant{OPattern}, Int)

Create determinant and calculate phase factor for single alpha excitation i -> a.

source
ElemCo.FCI.single_beta_excitation_phaseMethod
single_beta_excitation_phase(det::Determinant, orb_i::Int, orb_a::Int) -> (Determinant{OPattern}, Int)

Create determinant and calculate phase factor for single beta excitation i -> a.

source
ElemCo.FCI.single_excitation_alphaMethod
single_excitation_alpha(det::Determinant{OPattern}, i::Int, a::Int) where OPattern -> Determinant{OPattern}

Create determinant with alpha electron moved from orbital i to orbital a.

source
ElemCo.FCI.single_excitation_betaMethod
single_excitation_beta(det::Determinant{OPattern}, i::Int, a::Int) where OPattern -> Determinant{OPattern}

Create determinant with beta electron moved from orbital i to orbital a.

source
ElemCo.FCI.slater_condon_allowedMethod
slater_condon_allowed(det_i::Determinant, det_j::Determinant) -> Bool

Check if two determinants differ by at most two orbital occupations (same, single, or double excitations). Returns true if they differ by ≤ 2 orbitals, false otherwise.

source
ElemCo.FCI.solve_projected_pspace_systemMethod
solve_projected_pspace_system(r_P::Vector{Scalar}, u_P::Vector{Scalar}, 
                              theta::Scalar, pspace_data::PSpaceData, 
                              shift::Scalar, alpha::Scalar)

Solve the projected P-space correction equation with Q-space coupling: [(I - uP*uP^T)(HPP - θI)(I - uPu_P^T) + αuP*uP^T] tP = rP

This is part of the Jacobi-Davidson P-Q coupled preconditioner algorithm. The α term accounts for energy shift from Q-space component of Ritz vector.

Arguments:

  • r_P: Residual vector in P-space
  • u_P: Current Ritz vector in P-space (should be normalized)
  • theta: Current Ritz value (approximate eigenvalue)
  • pspace_data: P-space data structure with Hamiltonian
  • shift: Level shift for regularization
  • alpha: Q-space energy shift term (α = uQ^T(HQQ - E)u_Q)

Returns: Correction vector tP (orthogonal to uP)

source
ElemCo.FCI.sum_h1e2Method
sum_h1e2(h1e2, occ::AbstractVector, a, i) -> Float64

Compute Σ_j h1e2[j, a, i] over occupied orbitals j.

source
ElemCo.FCI.sum_h1e2Method
sum_h1e2(h1e2, str::OPattern, a, i) where OPattern -> Float64

Compute Σ_j h1e2[j, a, i] over occupied orbitals j.

source
ElemCo.FCI.sym_dofMethod
sym_dof(N::Integer, ndim::Integer) -> UInt64

Number of symmetric degrees of freedom for dimension ndim.

source
ElemCo.FCI.trip_indexMethod
trip_index(p, q, n) -> Int

Compute unique index for orbital pair (p, q), with n orbitals per spin.

source
ElemCo.FCI.update_ci_vector!Function
update_ci_vector!(c::FCIVector, r::FCIVector, diag_h::FCIVector,
                 energy::Scalar, context::FCIContext, shift::Scalar,
                 u::Union{FCIVector,Nothing}=nothing)

Update CI vector using Davidson preconditioner with optional Jacobi-Davidson projection.

Two modes available:

  1. Jacobi-Davidson (jacobi_davidson=true, default): Uses projection to prevent linear dependency Requires current Ritz vector u to be provided
  2. Simple preconditioner (jacobi_davidson=false)

When P-space is available: uses exact solution in P-space + diagonal preconditioner in Q-space. When P-space is not available: falls back to standard diagonal preconditioner.

Arguments:

  • c: Output correction vector
  • r: Residual vector
  • diag_h: Diagonal Hamiltonian elements
  • energy: Current energy estimate
  • context: FCI context
  • shift: Level shift for regularization
  • u: Current Ritz vector (normalized approximate eigenvector). Required for Jacobi-Davidson mode.
source
LinearAlgebra.dotMethod
LinearAlgebra.dot(a::FCIVector{OPattern}, b::FCIVector{OPattern}) where OPattern -> Scalar

Compute dot product using LinearAlgebra.

source
LinearAlgebra.normMethod
LinearAlgebra.norm(vec::FCIVector{OPattern}) where OPattern -> Scalar

Compute norm of FCI vector using LinearAlgebra.

source