クイックリファレンス: 変数と式

qbpp::Exprで使用されるデータ型

  • coeff_t: qbpp::Termオブジェクトの係数に使用される整数データ型。デフォルトはint32_t
  • energy_t: qbpp::Exprオブジェクトのエネルギー値の計算、およびqbpp::Expr内の整数定数項に使用される整数データ型。デフォルトはint64_tenergy_tのビット幅はcoeff_tのビット幅以上であることが保証されています。

これらの型はプリビルド済みの共有ライブラリとセットで提供されており、 ヘッダをインクルードする前に次の INTEGER_TYPE_* マクロのいずれかを定義して切り替えます (コンパイラフラグ -D... でも指定可能):

マクロ coeff_t energy_t
INTEGER_TYPE_C32E32 int32_t int32_t
INTEGER_TYPE_C32E64(デフォルト) int32_t int64_t
INTEGER_TYPE_C64E64 int64_t int64_t
INTEGER_TYPE_C64E128 int64_t int128_t
INTEGER_TYPE_C128E128 int128_t int128_t
INTEGER_TYPE_CPP_INT cpp_int cpp_int

注意 — オーバーフロー. coeff_t は各係数を、energy_t は累積エネルギー(有効な項の総和)を制限します。固定幅の型はオーバーフローを検出しません。累積エネルギーが energy_t を超えると、C++ の組み込み整数演算と同じく黙って折り返します。最悪ケースのエネルギーを収められる energy_t を持つバリアントを選んでください。INTEGER_TYPE_CPP_INT(任意精度)はオーバーフローしません。

実数(double)係数

係数は double(実数)にもできます。INTEGER_TYPE_* の代わりに次の DOUBLE_TYPE* マクロの いずれかを定義すると、coeff_tenergy_t はともに double になります:

マクロ coeff_t energy_t 求解に使うソルバー
DOUBLE_TYPE(= DOUBLE_TYPE_C64E64 double double 64ビット整数ソルバー
DOUBLE_TYPE_C128E128 double double 128ビット整数ソルバー(高精度)
#define DOUBLE_TYPE
#include <qbpp/qbpp.hpp>

auto x = qbpp::var("x");
auto y = qbpp::var("y");
qbpp::Expr f = -1.5 * x - 2.5 * y + 4.0 * x * y;   // 実数(double)係数
  • 式の構築・簡約・評価はすべて double で行われ、sol.energy()double を返します。
  • 求解時には係数が自動的に整数へスケーリングされ、上記の整数ソルバーに渡されます — 手動の量子化は不要です。
  • 2進小数の係数(1, 1/2, 1/4, …)は厳密に表現されます。最大係数よりはるかに小さい係数は スケーリング精度を下回ると通知付きでドロップされます。DOUBLE_TYPE_C128E128 を使うと ダイナミックレンジが大幅に広がります。
  • 除算(/, /=)は実数除算です — 整数バリアントの割り切れ要件は適用されません。
  • MAXDEG* は整数バリアントと同様に組み合わせ可能です(例: DOUBLE_TYPE + MAXDEG2)。
  • 定数配列や qbpp::einsum にも double 値を渡せます(MULTIDIM / EINSUM 参照)。

詳しくは 実数(double)係数 を参照してください。

さらに、各 qbpp::Term が変数をどう格納するかを制御する MAXDEG* マクロも指定できます。 最大次数が事前に分かっている場合、固定長モードを使うとヒープ確保が不要になり性能が向上します:

マクロ 最大次数 説明
MAXDEG0(デフォルト) 無制限 可変長(3次以上でヒープ確保)
MAXDEG2 2 固定長、QUBO専用(ヒープ確保なし、最速)
MAXDEG4 4 固定長、4次まで(ヒープ確保なし)

INTEGER_TYPE_*MAXDEG* は独立に組み合わせ可能です。詳細は VAREXPR を参照してください。

WARNING パフォーマンスを最大化するため、QUBO++は算術オーバーフローのチェックを行いません。 開発およびテスト中は、coeff_tenergy_tにはより広いビット幅を使用することを推奨します。 必要なビット幅が不明な場合は、qbpp::cpp_intを使用して正確性を確保し、 検証後に固定幅の整数型に切り替えてください。

クラスオブジェクトの出力

QUBO++のほとんどのクラスは、std::ostream<<演算子を使用して出力でき、 デバッグに便利です。 例えば、QUBO++のオブジェクトobjは次のようにstd::coutに出力できます:

std::cout << obj << std::endl;

この設計により、デバッガに頼ることなく内部状態を簡単に確認できます。

変数クラス

  • qbpp::Var: 一意な32ビット整数IDを保持するクラス。 変数名はグローバルレジストリに格納され、std::cout << xで確認できます。

注意 qbpp::Varオブジェクトは変数をシンボリックに表現します。 特定のデータ型は関連付けられていません。 バイナリ、スピン、その他の型の変数を表現するために使用できます。

変数作成関数

変数を作成するために以下の関数が提供されています:

  • qbpp::var("name"): 指定された名前"name"を持つqbpp::Varオブジェクトを作成します。

  • qbpp::var("name", s1): ベース名"name"を持つqbpp::Varオブジェクトの1次元配列を作成します。 各要素はname[i]として表現されます。 結果は1次元の変数の配列です。

  • qbpp::var("name", s1, s2): ベース名"name"を持つqbpp::Varオブジェクトの2次元配列(行列)を作成します。 各要素はname[i][j]として表現されます。 結果は2次元の変数の配列です。

  • qbpp::var("name", s1, s2, ...): ベース名"name"を持つqbpp::Varオブジェクトの高次元配列を作成します。 各要素はname[i][j]...として表現されます。 結果はN次元の変数の配列です(Nは次元数)。

注意 "name"が省略された場合、"{0}""{1}"、…のような番号付きの名前が作成順に自動的に割り当てられます。

qbpp::Varメンバ関数

qbpp::Varのインスタンスxに対して、以下のメンバ関数が利用できます:

  • uint32_t x.index(): xの一意な整数IDを返します。

通常、QUBO++プログラムでこれらのメンバ関数を明示的に呼び出す必要はありません。

整数変数

整数変数は、範囲とビット分解のメタデータを保持する qbpp::Expr であり、指定された範囲の整数値を表現します。

整数変数作成関数

整数変数を作成するために以下の関数が提供されています:

  • qbpp::var_int("name"): 内部的に使用されるヘルパーオブジェクトを返し、単体では整数変数を作成しません。 整数変数を定義するには、以下に示すように<=演算子を使用して範囲を指定する必要があります。

  • l <= qbpp::var_int("name") <= u: ここでluは整数でなければなりません。 この式は名前"name"を持つ整数変数の qbpp::Expr オブジェクトを作成し、 保持する式が範囲[l, u]のすべての整数を表現します。 内部的には、基礎となる式で使用されるqbpp::Varオブジェクトも作成されます。

  • l <= qbpp::var_int("name", s1) <= u: ベース名"name"と同じ範囲[l, u]を持つ整数変数 qbpp::Expr の1次元配列を作成します。 各要素はname[i]として表現されます。 結果は1次元の整数変数の配列です。 整数変数の高次元配列は qbpp::Var オブジェクトと同じ方法で作成できます。

整数変数メンバ関数

整数変数 xqbpp::Expr)に対して、以下のメンバ関数が利用できます:

  • energy_t x.min_val(): xの最小値lを返します。

  • energy_t x.max_val(): xの最大値uを返します。

  • Array<1, Var> x.vars(): 整数変数を表現するために使用されるqbpp::Varオブジェクト配列を返します。

  • Array<1, coeff_t> x.coeffs(): 整数係数配列を返します。

以下の式はxに格納されている式と等価です:

qbpp::sum(x.coeffs() * x.vars()) + x.min_val()

Back to top

Page last modified: 2026.07.09.