Files
DotsToSirface/backend/pipeline_insights.py
T
gitrusprusandCursor 4f253b860f Реструктуризация проекта и генератор синтетических датасетов эхолота.
Перенесены backend/frontend/desktop/engine, добавлены вкладки конструктора сцен и генератора датасета с параметрами лучей и длины сетки рельефа, обновлены API и Docker-сборка.

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-07-17 12:25:00 +03:00

67 lines
2.9 KiB
Python

"""Pipeline chain insights (mirrors MainWindow::recomputeInsights)."""
from __future__ import annotations
from typing import Any
def compute_insights(
preprocess_plugins: list[str],
reconstruction_plugin: str,
) -> dict[str, Any]:
warnings: list[str] = []
risk_state = False
stages = [s for s in preprocess_plugins if s]
voxel_idx = stages.index("pcl_voxel_grid") if "pcl_voxel_grid" in stages else -1
remove_nan_idx = stages.index("pcl_remove_nan") if "pcl_remove_nan" in stages else -1
remove_nan_normals_idx = (
stages.index("pcl_remove_nan_normals") if "pcl_remove_nan_normals" in stages else -1
)
outlier_indexes = []
for stage_id in (
"pcl_statistical_outlier",
"pcl_radius_outlier",
"pcl_model_outlier",
"pcl_shadow_points",
):
if stage_id in stages:
outlier_indexes.append(stages.index(stage_id))
first_outlier_idx = min(outlier_indexes) if outlier_indexes else -1
if not stages:
risk_state = True
warnings.append("Добавьте хотя бы один этап препроцессинга перед реконструкцией.")
else:
if first_outlier_idx < 0:
warnings.append("Добавьте outlier removal для стабилизации триангуляции.")
if first_outlier_idx >= 0:
nan_idxs = [i for i in (remove_nan_idx, remove_nan_normals_idx) if i >= 0]
first_nan_preclean_idx = min(nan_idxs) if nan_idxs else -1
if first_nan_preclean_idx < 0 or first_nan_preclean_idx > first_outlier_idx:
warnings.append(
"Удалите NaN сразу после загрузки/обрезки: иначе статистические фильтры работают нестабильно."
)
if voxel_idx >= 0 and first_outlier_idx >= 0 and first_outlier_idx > voxel_idx:
warnings.append(
"OutlierRemoval стоит после VoxelGrid: лучше сначала очистить шум, затем прореживать."
)
if reconstruction_plugin == "pcl_greedy_triangulation" and voxel_idx < 0:
warnings.append("Greedy triangulation обычно работает лучше после voxel downsampling.")
if risk_state:
chain_health = "Risk"
recommendation = warnings[0] if warnings else "Проверьте порядок этапов пайплайна."
elif warnings:
chain_health = "Warning"
recommendation = warnings[0]
else:
chain_health = "OK"
recommendation = "Пайплайн сбалансирован. Используйте «Сохр. конф.» для A/B-сравнения."
return {
"chainHealth": chain_health,
"warningsList": warnings,
"recommendation": recommendation,
}