mcpField
C
cufolio

cufolio

github.com/promptingcompanyデータ・データベース039 回インストール17 週間前に更新
リポジトリ

cufolio について

cuFOLIO Skill は NVIDIA GPU 加速の Mean-CVaR 手法で、定量ポートフォリオを構築・分析します。cuFOLIO パッケージを使い、シナリオ生成、効率的フロンティア分析、バックテスト、リバランスを行い、ソルバーには cuOpt GPU を使用します。

主な機能

  1. 01リターン計算と KDE シナリオ生成
  2. 02cuOpt による Mean-CVaR 配分最適化
  3. 03効率的フロンティアとリスク別ウェイト表
  4. 04ベンチマークとのバックテスト
  5. 05日程またはドリフト条件でリバランス

活用シーン

  1. 01株価から下方 CVaR を抑えたポートフォリオを最適化
  2. 02リスク許容度ごとの資産ウェイトを確認
  3. 03最適化配分を均等配分と比較してバックテスト
  4. 04月次またはドリフト発生時に保有配分を調整

インストール

コマンドをコピーしてターミナルで実行します。

$npx skills add https://github.com/promptingcompany/nv-skills --skill cufolio

インストール後、Claude Code で/cufolioを入力して読み込まれたか確認します。

同梱ファイル

SKILL.md と一緒にインストールされる参考資料やスクリプト。

BENCHMARK.md
skill-card.md
skill.oms.sig
evals/
EVAL.md
evals-full.json
evals.json
references/workflows/
agent_recipes.md

詳細

cuFOLIO スキル

目的

NVIDIA によって高速化された Mean-CVaR 最適化を使用して、定量ポートフォリオを構築・分析します。cuFOLIO を使用してリターンを計算し、KDE シナリオを生成し、cuOpt GPU ソルバーで配分を解き、効率的フロンティアを追跡し、ポートフォリオをバックテストし、価格データからリバランスのワークフローを実行します。

使用するタイミング

次のタスクを行う場合に、このスキルを使用します。

  • 株価から Mean-CVaR ポートフォリオを構築または最適化する。
  • 下方 CVaR リスクを抑えながら、ティッカー間のウェイトを配分する。
  • ポートフォリオの投資対象全体について、効率的フロンティアをプロットまたは確認する。
  • リスク許容度別のウェイト表を作成する。
  • 最適化したポートフォリオをベンチマークと比較してバックテストする。
  • スケジュールまたはドリフトのトリガーに基づいてポートフォリオをリバランスする。
  • S&P 500、S&P 100、Dow 30、またはユーザーが指定した価格データセットでワークフローを実行する。

一般的なトリガーフレーズには、「ポートフォリオを最適化して」「CVaR ポートフォリオを構築して」「これらのティッカーに cuFOLIO を使って」「cuOpt で解いて」「効率的フロンティアをプロットして」「リスク許容度別のウェイトを表示して」「この配分をバックテストして」「毎月リバランスして」「保有資産を CVaR で分析して」「配分を比較して」「下方リスクを低減して」「配分を構成して」「配分の選択肢を評価して」「保有資産のストレステストをして」「下方リスクへのエクスポージャーを評価して」「ウェイト上限のもとで保有資産を見直して」「ベンチマークポートフォリオを比較して」「CVaR シナリオをシミュレーションして」「ポートフォリオのリスクをスクリーニングして」「制約条件下で保有資産を最適化して」「より低リスクの配分を探して」などがあります。

一般的な金融の要約、価格予測、ニューラルネットワークのトレーニング、車両経路問題、ポートフォリオ以外の最適化には使用しないでください。

前提条件

  • cufolio パッケージがインストールされた Python 環境。
  • cuOpt と cuML がインストールされた NVIDIA GPU ランタイム。
  • ホストに適合する CUDA エクストラ(例:uv sync --extra cuda12 または uv sync --extra cuda13)。
  • cp.CUOPT を公開する cvxpy。
  • デフォルトの価格 CSV をダウンロードする必要がある場合は、初回実行時にネットワークアクセスが必要です。

セットアップ

このスキルは、インストール済みの cufolio パッケージを使用します。利用可能な環境は、Brev のランチャブル環境、または対応する CUDA エクストラをインストールした NVIDIA-AI-Blueprints/cuFOLIO から用意できます。

パッケージ化されたエージェント/評価用サンドボックスでは、cufolio が個別に公開された wheel ではなく、PYTHONPATH 経由で利用できる場合があります。不足していると判断する前に、python -c "import cufolio" でローカルパッケージを確認してください。pip install cufolio は実行せず、cuFOLIO のワークフローを一から再実装せず、パッケージ API を汎用的な pandas/scipy/cvxpy のポートフォリオコードに置き換えないでください。

具体的な実装の詳細については、信頼できる情報源である references/workflows/agent_recipes.md を参照してください。価格の読み込み、リターンの準備、cuOpt での最適化、25 点のフロンティアの構築、等ウェイトとのバックテスト、リバランサーの呼び出しについて、実際に動作する正確な形式が記載されています。

デフォルトのデータセットは data/stock_data/sp500.csv です。これは Git の追跡対象外です。初回ダウンロードの前に、cuFOLIO/yfinance のデータヘルパーを通じて公開市場データを取得することをユーザーに伝え、次の操作について確認を得てください。

import cvxpy as cp
from cufolio.cvar_parameters import CvarParameters
from cufolio.utils import download_data

download_data("data/stock_data", datasets=["sp500"])
SOLVER_SETTINGS = {"solver": cp.CUOPT, "verbose": False, "solver_method": "PDLP"}
cvar_params = CvarParameters(
    w_min=0.0, w_max=1.0,
    c_min=0.0, c_max=0.0,
    risk_aversion=1.0, confidence=0.95,
)

手順

実行前に適用するデフォルトを簡潔に述べてから、次のガードレールに従ってください。

  1. data/stock_data/sp500.csv を読み込みます。存在しない場合は、cufolio.utils.download_data で sp500 をダウンロードする前に確認してください。価格データを glob で検索したり、代替したり、捏造したりしないでください。
  2. 解決に取りかかる前に、ユーザーの CSV を検証します。日付形式のインデックスまたは最初の日付列、数値形式のティッカー列、日付でフィルタリングした後に少なくとも 60 行、そしてリクエストされたティッカーが少なくとも 1 つ含まれていることを必須とします。ユーザーが開始日/終了日を指定した場合は、リターンを計算する前に価格 DataFrame をスライスし、保持された日付範囲を報告します。リターンの計算前に、価格 DataFrame でティッカーをフィルタリングしてください。regime_dict はティッカーフィールドを受け取りません。
  3. utils.calculate_returns(...) を使って LOG リターンを計算します。
  4. KDE と KDESettings(device="GPU") を使い、cvar_utils.generate_cvar_data(...) でシナリオを生成します。
  5. CvarParameters は、明示的な w_min と w_max を指定して定義します。通常の「最適ポートフォリオを構築する」リクエストでは、現金 100% ではなく全額投資となるよう、c_min=0.0 と c_max=0.0 を設定します。
  6. リターン辞書から直接 cvar_optimizer.CVaR(returns_dict, cvar_params) を構築します。ティッカー、シナリオ配列、平均値、共分散は、cuFOLIO ヘルパーが返す形状のまま維持してください。
  7. NVIDIA cuOpt のみを使って解きます。解く前に、hasattr(cp, "CUOPT") と str(cp.CUOPT) in {str(s) for s in cp.installed_solvers()} を確認してください。単発の solve またはループによるフロンティア solve のすべてに SOLVER_SETTINGS を渡してください。CLARABEL、SCS、ECOS、その他の CPU ソルバーには決してフォールバックしないでください。cuOpt が利用できない場合は、検証とセットアップを完了したうえで、GPU/cuOpt ランタイムが不足していると報告し、CPU による結果を捏造しないでください。
  8. カスタム制約は、ユーザーのリクエストを CvarParameters に対応付けます。ウェイト上限は w_min/w_max、リスク許容度は risk_aversion、信頼水準は confidence、現金の許容額は c_max に対応付けます。カーディナリティ制約は、そのワークフローでパッケージが明示的な資産数制約を公開している場合に限り適用します。制約が両立しない場合(たとえば、指定されたティッカー数に対して最大ウェイトが低すぎる場合)は、どの制約を緩和するかを推測せず、矛盾を説明して確認してください。
  9. ユーザーがバックテストのベンチマークを指定しない場合は、同じティッカーを使った均等ウェイトのポートフォリオを使用します。制約が指定されていない場合は、デフォルト表の値を維持し、解く前に重要な前提を簡潔に言い直してください。
  10. 配分順に並べたウェイト、現金ウェイト、期待リターン、CVaR、ソルバーラベル(cuOpt GPU)、およびリクエストされたフロンティア図、ウェイト表、バックテスト指標、またはリバランススケジュールを提示します。表では、ティッカーを列または行として含め、10進数のウェイトとパーセンテージを記載します。プロットでは、最初から描き直さず、返された cuFOLIO の図を保持してください。
  11. レポート品質が求められる回答では、リクエストされたワークフローを実際に実行した証拠を含めます。効率的フロンティアでは len(results_df) を示し、指定された ra_num(ユーザーの指定がない場合は 25)を使用します。ウェイト表では results_df["weights"] をティッカー列に展開し、cash と risk_aversion を含めます。バックテストでは、最適化ポートフォリオとベンチマークポートフォリオの両方について、mean portfolio return、sharpe、sortino、max drawdown を含めます。リバランスでは、results_dataframe、re_optimize_dates、および cumulative_portfolio_value の末尾を含めます。

標準的なワークフローのひな形

肯定的な cuFOLIO タスクはこの形式から始め、要求された出力だけに合わせて調整してください。コピーして使える完全な関数については、カスタムコードを書く前に references/workflows/agent_recipes.md を読んでください。

import cvxpy as cp
import pandas as pd

from cufolio import backtest, cvar_optimizer, cvar_utils, rebalance, utils
from cufolio.cvar_parameters import CvarParameters
from cufolio.portfolio import Portfolio
from cufolio.settings import KDESettings, ReturnsComputeSettings, ScenarioGenerationSettings

if not hasattr(cp, "CUOPT") or str(cp.CUOPT) not in {str(s) for s in cp.installed_solvers()}:
    raise RuntimeError("cuOpt GPU solver is required; do not substitute a CPU solver.")

SOLVER_SETTINGS = {"solver": cp.CUOPT, "verbose": False, "solver_method": "PDLP"}

prices = utils.get_input_data("data/stock_data/sp500.csv")
returns_dict = utils.calculate_returns(
    prices,
    regime_dict=None,
    returns_compute_settings=ReturnsComputeSettings(return_type="LOG"),
)
returns_dict = cvar_utils.generate_cvar_data(
    returns_dict,
    ScenarioGenerationSettings(
        fit_type="kde",
        kde_settings=KDESettings(device="GPU"),
    ),
)
cvar_params = CvarParameters(
    w_min=0.0,
    w_max=1.0,
    c_min=0.0,
    c_max=0.0,
    risk_aversion=1.0,
    confidence=0.95,
)
optimizer = cvar_optimizer.CVaR(returns_dict, cvar_params)
result, optimal_portfolio = optimizer.solve_optimization_problem(
    solver_settings=SOLVER_SETTINGS,
    print_results=False,
)

効率的フロンティアまたはウェイトの表を作成するには、次を呼び出します。

results_df, fig, ax = cvar_utils.create_efficient_frontier(
    returns_dict,
    cvar_params,
    SOLVER_SETTINGS,
    ra_num=25,
    show_plot=False,
    show_discretized_portfolios=False,
    benchmark_portfolios=False,
    print_portfolio_results=False,
)
weights_table = pd.DataFrame(results_df["weights"].tolist(), index=results_df.index)

ベンチマークのバックテストを行う場合は、解決済みのアロケーションを Portfolio(name="cuOpt Optimal", tickers=returns_dict["tickers"], weights=optimal_portfolio.weights, cash=optimal_portfolio.cash) でラップし、同じ returns_dict["tickers"] を使ってイコールウェイトの Portfolio を作成してから、backtest.portfolio_backtester(..., test_method="historical").backtest_against_benchmarks(...) を使用します。バックテスターは (backtest_results, ax) を返します。

月次リバランスを行う場合は、まず価格の DataFrame を CSV パスに書き込みます。re_optimize_criteria={"type": "drift_from_optimal", "threshold": 0, "norm": 1} を指定して rebalance.rebalance_portfolio(dataset_directory=<csv_path>, ...) をインスタンス化し、re_optimize(transaction_cost_factor=..., plot_title="Monthly Rebalancing") を呼び出します。リバランサーは (results_dataframe, re_optimize_dates, cumulative_portfolio_value) を返します。

データとデフォルト値

設定デフォルト
データセットdata/stock_data/sp500.csv
期間利用可能な全期間
ポートフォリオの種類ロングのみ
最大ウェイト指定がない場合はなし
リスク回避度1.0
信頼度0.95
シナリオ手法GPU 上の KDE
ソルバーPDLP を使用する cuOpt GPU
リバランス要求がない場合はなし

デフォルトの S&P 500 ファイルは過去の時点のスナップショットであり、現在の構成銘柄が含まれていない場合があります。ユーザー提供の CSV は、utils.get_input_data と互換性のある、ティッカー列を含む日付インデックス付きの価格テーブルにしてください。要求されたティッカーが存在しない場合は、それらを除外し、除外した銘柄を報告したうえで、ユーザーが別のデータの取得を明示的に要求していない限り、利用可能な列を使って処理を続けてください。

主な API

ポートフォリオの計算やシミュレーションループを再実装せず、パッケージの API を使用してください。cuFOLIO のヘルパーが返すのはフラットなオブジェクトです。returns_dict には returns、mean、covariance、tickers などのキーが含まれます。returns_dict["regime_1"] のようにインデックスを指定しないでください。solve_optimization_problem(...) が返すのは (result_row, portfolio) であり、入れ子の結果辞書ではありません。

  • リターン:utils.calculate_returns(input_dataset, regime_dict, returns_compute_settings)。
  • レジームフィルター:regime_dict は None または {"name": "...", "range": ("YYYY-MM-DD", "YYYY-MM-DD")} です。レジーム名をキーにした辞書ではなく、ティッカーも含みません。
  • シナリオ:cvar_utils.generate_cvar_data(returns_dict, scenario_generation_settings)。
  • オプティマイザー:cvar_optimizer.CVaR(returns_dict, cvar_params)。
  • 解決:result_row, portfolio = cvar_problem.solve_optimization_problem(solver_settings=SOLVER_SETTINGS, print_results=False)。
  • 効率的フロンティア:cvar_utils.create_efficient_frontier(returns_dict, cvar_params, solver_settings=SOLVER_SETTINGS, ra_num=25)。返される results_df には、指標、weights の辞書列、cash が含まれます。
  • ポートフォリオ:Portfolio(name="", tickers=None, weights=None, cash=0.0, time_range=None)。ティッカーと、それらに対応するフラットな配列形式の weights を渡してください。
  • バックテスト:最適化されたアロケーションと各ベンチマークについて portfolio.Portfolio オブジェクトを作成します。イコールウェイトのベンチマークには、重み 1 / len(tickers) と cash=0.0 を使用し、backtest.portfolio_backtester(test_portfolio, returns_dict, risk_free_rate=0.0, test_method="historical", benchmark_portfolios=[...]).backtest_against_benchmarks(...) を呼び出してください。
  • リバランス:rebalance.rebalance_portfolio(...) の dataset_directory には DataFrame ではなく CSV パスを指定する必要があります。re_optimize(...) を呼び出してください。返されるのは (results_dataframe, re_optimize_dates, cumulative_portfolio_value) です。
  • 設定モデル:ReturnsComputeSettings、ScenarioGenerationSettings、KDESettings、ApiSettings、CvarParameters。

例

  • 「S&P 500 から最適なポートフォリオを構築する」:価格を読み込み、LOG リターンを計算し、GPU KDE シナリオを生成して、ロングオンリーで全額投資する CvarParameters を設定し、cuOpt で解き、分散されたウェイトとリターン/CVaR を報告します。
  • 「効率的フロンティアをプロットする」:create_efficient_frontier(...) を呼び出し、results_df を返して、要求に応じて図を表示または保存します。
  • 「リスク回避度ごとのウェイトを教えて」:results_df["weights"] を銘柄ごとのテーブルに展開します。
  • 「均等加重と比較してバックテストする」:最適化ポートフォリオと均等加重ポートフォリオの Portfolio オブジェクトを作成し、cuFOLIO のバックテスターを使用して、シャープレシオ、ソルティノレシオ、最大ドローダウンを報告します。
  • 「月次リバランスでバックテストする」:上記のドリフトトリガーを使って rebalance_portfolio を設定し、re_optimize(transaction_cost_factor=...) を実行します。

制限事項

  • cuOpt と cuML を備えた NVIDIA GPU が必要です。CPU ソルバーは意図的に使用できないようになっています。
  • CPU のみの評価コンテナーでも、ルーティング、データ処理、レポート動作は検証できますが、有効な cuOpt ソルバー実行はできません。その場合は、GPU/cuOpt ランタイムがないことを明示してください。
  • デフォルトの価格データは過去のスナップショットであり、現在の構成銘柄が含まれていない場合があります。
  • 初回のデータセットダウンロードには、ユーザーから CSV が提供されない限り、ネットワーク接続が必要です。

トラブルシューティング

  • デフォルトの CSV がない、または FileNotFoundError が発生する場合:cuFOLIO は download_data("data/stock_data", datasets=["sp500"]) で公開市場データを取得することを説明してください。実行するのはユーザーの確認後に限ります。
  • SolverError または cp.CUOPT がない場合:ホスト環境に合った CUDA 追加パッケージをインストールし、python -c "import cvxpy as cp; print(hasattr(cp, 'CUOPT'), cp.installed_solvers())" で確認してください。
  • cuml の ImportError または GPU KDE の失敗が発生する場合:python -c "import cuml" で cuML があることを確認し、KDESettings(device="GPU") を維持してください。
  • 通常の最適化で現金のみが返される場合:CvarParameters で c_max=0.0 を設定してください。
  • ソルバーが実行不可能または解なしと報告する場合:矛盾する境界条件、要求された上限/銘柄数制約に対するティッカー数の不足、またはデータが少なすぎる日付フィルターがないかを確認し、要求を実行可能にするために変更が必要な制約を最小限で報告してください。
  • 要求されたティッカーがデフォルトの CSV にない場合:該当するティッカーを報告し、残りの要求されたティッカーで続行してください。
  • ユーザーの CSV が検証に失敗する場合:日付をインデックスとする価格テーブル、または最初の列が日付で残りの列が数値のティッカー価格である CSV を求めてください。フィルター適用後に最低 60 行が必要であることも伝えてください。

コメント