{"record":{"id":"1e2b12113d0c324f","repo":"HKUDS/Vibe-Trading","slug":"paths-must-be-2-d-with-2-columns-got-shape-ma","errorCode":null,"errorMessage":"paths must be 2-D with >= 2 columns, got shape {matrix.shape}","messagePattern":"paths must be 2-D with >= 2 columns, got shape (.+?)","errorType":"exception","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"agent/src/quantlib/risk.py","lineNumber":603,"sourceCode":"    Returns:\n        dict with keys:\n            mean_return, median_return, std_return (float): Signed total\n                returns over the simulation, so a bad outcome is negative.\n            var, cvar (float): Positive loss magnitudes, computed with the same\n                order-statistic convention as ``historical_var`` /\n                ``historical_cvar``, so ``cvar >= var``.\n            prob_loss (float): Fraction of paths ending below their start.\n            worst_5pct_return, best_5pct_return (float): Signed 5th and 95th\n                percentiles of the terminal return (linear interpolation).\n\n    Raises:\n        ValueError: If ``paths`` is not 2-D with at least two columns, holds a\n            non-positive starting price, or ``confidence`` is outside (0, 1).\n    \"\"\"\n    _validate_confidence(confidence)\n    matrix = np.asarray(paths, dtype=float)\n    if matrix.ndim != 2 or matrix.shape[1] < 2:\n        raise ValueError(f\"paths must be 2-D with >= 2 columns, got shape {matrix.shape}\")\n    start = matrix[:, 0]\n    if (start <= 0.0).any():\n        raise ValueError(\"paths column 0 (the starting price) must be strictly positive\")\n\n    returns = matrix[:, -1] / start - 1.0\n    return {\n        \"mean_return\": float(np.mean(returns)),\n        \"median_return\": float(np.median(returns)),\n        \"std_return\": float(np.std(returns, ddof=1)) if returns.size > 1 else 0.0,\n        \"var\": historical_var(returns, confidence),\n        \"cvar\": historical_cvar(returns, confidence),\n        \"prob_loss\": float(np.mean(returns < 0.0)),\n        \"worst_5pct_return\": float(np.percentile(returns, 5.0)),\n        \"best_5pct_return\": float(np.percentile(returns, 95.0)),\n    }\n\n\ndef fit_gpd_tail(","sourceCodeStart":585,"sourceCodeEnd":621,"githubUrl":"https://github.com/HKUDS/Vibe-Trading/blob/80ffdda44c5c4db0dd84d70e051cca591cea67df/agent/src/quantlib/risk.py#L585-L621","documentation":"analyze_mc_results expects a 2-D matrix of simulated paths where each row is a path and column 0 is the starting price; it computes terminal returns as matrix[:, -1]/matrix[:, 0] - 1. Fewer than 2 columns means there is no terminal point distinct from the start, so no return exists; 1-D or 3-D input is likewise rejected.","triggerScenarios":"analyze_mc_results(np.array([100, 105, 98])) (a single 1-D path), a matrix with shape (n, 1) (start only, no steps), or an (n, k, m) tensor.","commonSituations":"Analyzing one path instead of the batch (forgetting paths[None, :]); simulation returning paths without the s0 column; accidental .ravel() flattening the matrix before analysis.","solutions":["Ensure shape is (n_paths, n_steps+1) with column 0 = s0 (as monte_carlo_gbm returns)","Add a batch dimension for one path: path[None, :]","Do not flatten the matrix; check matrix.ndim == 2 and shape[1] >= 2 before calling"],"exampleFix":"// before\nstats = analyze_mc_results(single_path)  # 1-D\n// after\nstats = analyze_mc_results(single_path[None, :])  # shape (1, n+1), s0 in col 0","handlingStrategy":"type-guard","validationCode":"import numpy as np\nm = np.asarray(paths, dtype=float)\nassert m.ndim == 2 and m.shape[1] >= 2, f\"need (n_paths, n_steps+1), got {m.shape}\"","typeGuard":"import numpy as np\n\ndef is_valid_path_matrix(x) -> bool:\n    m = np.asarray(x, dtype=float)\n    return m.ndim == 2 and m.shape[1] >= 2","tryCatchPattern":"try:\n    stats = analyze_mc_results(paths)\nexcept ValueError as e:\n    if \"2-D with >= 2 columns\" in str(e):\n        stats = analyze_mc_results(np.atleast_2d(paths))\n    else:\n        raise","preventionTips":["Feed monte_carlo_gbm output directly (it already has s0 in col 0)","Add a batch axis for single paths","Never ravel() a path matrix before analysis"],"tags":["quantlib","risk","monte-carlo","matrix-shape","valueerror"],"backgroundTag":"wrong-array-shape","analyzedSha":"80ffdda44c5c4db0dd84d70e051cca591cea67df","analyzedAt":"2026-08-28T12:46:38.989Z","schemaVersion":2},"datasetVersion":"2026-08-28T16:17:29.566Z"}