Skip to content

Conversation

@ajay-mk
Copy link
Member

@ajay-mk ajay-mk commented Feb 4, 2026

This PR extends support for Unitary ansatze in the CC class. UCC energies are verified against http://arxiv.org/abs/2503.00617.

Changes

  • Revamps CC constructor to enable designated initializer syntax. Some test/example cases had to be updated.
  • Truncation order for $\bar{H}$ commutator series can be specified in the constructor (necessary for Unitary ansatze), additional truncation ranks for similarity transformed perturbation operators can also be specified.
  • Add support for Unitary ansatze in eom_r and t' methods.
  • Updates mbpt::lst and mbpt::LSTOptions: when unitary ansatze are used, lst uses commutators to generate expansion unless specified otherwise.
  • CC::t() and CC::λ() no longer take commutator_rank parameter (now set via class constructor)
  • Updates and extends UCC unit tests (numerically verified).

- If unitary ansatz is used, truncation ranks must be specified
- If truncation values are not provided, will default to traditional ansatz ranks
- Since hbar is hermitian with unitary ansatz, all left amplitude methods are disabled
- Breaks API calls to t(), since the commutator_rank param is removed.
… on the ansatz.

use_commutators is now a std::optional<bool>. if it is not set, will be set to true for unitary ansatz and false otherwise.
Since the options object need to be modified, const qualification is removed and passed as a copy.
…eature/unitary-lr-and-eom

# Conflicts:
#	SeQuant/domain/mbpt/utils.cpp
Makes sense to do this, N does not have a default value.
Connectivity info is only built if unitary ansatz is not used.
Number of terms is updated, we also check different truncation ranks now.

These equations are numerically verified against http://arxiv.org/abs/2503.00617
This is a breaking change, but will be worth down the line.
Previously Flops::operator() assumed tensor products produced a tensor as a result. This throws an error from ContractedIndexCount when all indices are contracted.
Full contraction is now handled correctly and cost is computed  as 2 * O^occ * V^virt. Note that we only use the info from left, because it is a full contraction it will be the same as right.
See 0a237de. A new test case added which mimics CC energy expression.
# Conflicts:
#	SeQuant/core/eval/eval_node.hpp
@evaleev evaleev requested a review from Copilot February 4, 2026 03:10
@evaleev evaleev added this to the 2.1 milestone Feb 4, 2026
Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Extends the coupled-cluster (CC) derivation engine to better support unitary ansätze (UCC), including configurable commutator truncation ranks and updates to tests/examples to use the new constructor options API.

Changes:

  • Introduces CC::Options and refactors CC construction to support designated initializers and constructor-configured commutator truncation ranks.
  • Updates mbpt::lst / LSTOptions behavior so unitary ansätze default to explicit commutator expansions unless overridden.
  • Adds/updates UCC-related behavior in CC methods and adjusts unit/integration tests and documentation examples accordingly.

Reviewed changes

Copilot reviewed 7 out of 7 changed files in this pull request and generated 4 comments.

Show a summary per file
File Description
SeQuant/domain/mbpt/models/cc.hpp Adds CC::Options, new constructors, and updates t() / λ() signatures to use constructor-configured commutator ranks.
SeQuant/domain/mbpt/models/cc.cpp Implements new constructors and updates CC equation derivations to use configured truncation ranks; adds unitary handling in several methods.
SeQuant/domain/mbpt/utils.hpp Changes LSTOptions::use_commutators to std::optional<bool> and updates lst() signature/docs.
SeQuant/domain/mbpt/utils.cpp Implements defaulting logic for use_commutators and adjusts lst() to accept options by value.
tests/unit/test_mbpt_cc.cpp Updates UCC unit tests to use the new CC options-based constructor API and checks term counts per commutator rank.
tests/integration/srcc.cpp Updates integration usage to the new CC constructor + t()/λ() APIs.
doc/examples/user/cc.cpp Updates user-facing examples to use the new CC constructor options and fixes minor output variable usage.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

const bool skip_singles = ansatz_ == Ansatz::oT;

const auto commutator_rank =
hbar_comm_rank_.value_or(4); // default truncation rank is 4
Copy link

Copilot AI Feb 4, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

commutator_rank - 1 can underflow if hbar_comm_rank_ is configured as 0, and it also passes 0 into mbpt::lst() when hbar_comm_rank_ == 1 (but mbpt::lst() now asserts commutator_rank >= 1). Add validation/guarding here (e.g., require commutator_rank >= 2 for λ equations, or adjust lst() to allow rank 0 meaning "no commutators").

Suggested change
hbar_comm_rank_.value_or(4); // default truncation rank is 4
hbar_comm_rank_.value_or(4); // default truncation rank is 4
if (commutator_rank < 2) {
throw std::invalid_argument(
"CC::λ requires hbar_comm_rank >= 2 to construct hbar");
}

Copilot uses AI. Check for mistakes.
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See the comment below.

Comment on lines +33 to +39
use_topology_(opts.use_topology),
hbar_comm_rank_(opts.hbar_comm_rank),
pertbar_comm_rank_(opts.pertbar_comm_rank) {
if (unitary())
SEQUANT_ASSERT(hbar_comm_rank_ &&
"CC: hbar_comm_rank is required for unitary ansatz");
}
Copy link

Copilot AI Feb 4, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The new hbar_comm_rank_ / pertbar_comm_rank_ options are not range-validated. Values like 0 can later trigger underflow (commutator_rank - 1) or extremely large loops, and values <1 will also violate mbpt::lst()'s commutator_rank >= 1 precondition. Consider validating these options in the constructor (e.g., if set, require >= 1, and potentially >= 2 if λ() relies on rank-1).

Copilot uses AI. Check for mistakes.
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The assertion in lst has been removed (it wasn't supposed to be there). Having support for truncation rank 0 is beneficial. I have added an assertion in λ method to make sure arguments to lst are proper.
Additionally, when the truncation rank is zero (no commutators), $\bar{H} = H$, so calling λ does not make sense.

We do need to support commutator rank = 0 for other cases. At 0 truncation rank Hbar = H and hermitian. So λ does not make sense.
@ajay-mk ajay-mk marked this pull request as ready for review February 4, 2026 03:41
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants