重构爆管定位算法,增加多进程支持与可视化功能
This commit is contained in:
@@ -1,11 +1,14 @@
|
||||
import argparse
|
||||
import json
|
||||
import logging
|
||||
from multiprocessing import cpu_count
|
||||
from pathlib import Path
|
||||
from typing import Any, Iterable
|
||||
|
||||
import pandas as pd
|
||||
|
||||
from app.algorithms.burst_location import leak_simulator
|
||||
|
||||
from .burst_locator import (
|
||||
DN_search_multi_simple_add_flow_count_new,
|
||||
)
|
||||
@@ -18,7 +21,9 @@ from .network_model import (
|
||||
read_inf_inp_other,
|
||||
)
|
||||
|
||||
DEFAULT_N_WORKERS = max(1, min(cpu_count() - 1, 4))
|
||||
# DEFAULT_N_WORKERS = max(1, min(cpu_count() - 1, 4))
|
||||
DEFAULT_N_WORKERS = max(1, cpu_count() - 1)
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
def _read_id_list_json(path):
|
||||
@@ -115,6 +120,10 @@ def run_burst_location(
|
||||
min_dpressure: float = 2.0,
|
||||
basic_pressure: float = 10.0,
|
||||
n_workers: int = DEFAULT_N_WORKERS,
|
||||
partition_on_full_graph: bool = True,
|
||||
visualize_partition: bool = True,
|
||||
visualize_pause_seconds: float = 0.3,
|
||||
final_candidates_csv_path: str | None = "temp/burst_location/final_round_candidates.csv",
|
||||
) -> dict[str, Any]:
|
||||
if pressure_scada_ids is None or len(pressure_scada_ids) == 0:
|
||||
raise ValueError("pressure_scada_ids cannot be empty.")
|
||||
@@ -137,14 +146,30 @@ def run_burst_location(
|
||||
minimum_p=0.0,
|
||||
)
|
||||
|
||||
all_node, _, node_coordinates, candidate_pipe, _, _, pipe_length, _ = read_inf_inp(
|
||||
wn
|
||||
(
|
||||
all_node,
|
||||
_,
|
||||
node_coordinates,
|
||||
all_pipe,
|
||||
_,
|
||||
_,
|
||||
pipe_length,
|
||||
pipe_diameter,
|
||||
) = read_inf_inp(wn)
|
||||
|
||||
candidate_pipe, _ = leak_simulator.cal_possible_pipe(
|
||||
burst_leakage, all_pipe, pipe_diameter
|
||||
)
|
||||
|
||||
_, pipe_start_node_all, pipe_end_node_all = read_inf_inp_other(wn)
|
||||
node_x, node_y = cal_node_coordinate(all_node, node_coordinates)
|
||||
G0 = construct_graph(wn)
|
||||
node_pipe_dic, couple_node_length = _build_node_pipe_maps(
|
||||
all_node, candidate_pipe, pipe_start_node_all, pipe_end_node_all, pipe_length
|
||||
all_node,
|
||||
all_pipe,
|
||||
pipe_start_node_all,
|
||||
pipe_end_node_all,
|
||||
pipe_length,
|
||||
)
|
||||
all_node_series = pd.Series(range(len(all_node)), index=all_node)
|
||||
|
||||
@@ -176,43 +201,59 @@ def run_burst_location(
|
||||
max_flow = pd.Series(dtype=float)
|
||||
|
||||
stage_timing: dict[str, Any] = {}
|
||||
located_pipe, elapsed_seconds, simulation_times, _, similarity_series = (
|
||||
DN_search_multi_simple_add_flow_count_new(
|
||||
wn=wn,
|
||||
wn_inp_path=str(inp_path),
|
||||
G0=G0,
|
||||
all_node=all_node,
|
||||
node_x=node_x,
|
||||
node_y=node_y,
|
||||
pipe_start_node_all=pipe_start_node_all,
|
||||
pipe_end_node_all=pipe_end_node_all,
|
||||
couple_node_length=couple_node_length,
|
||||
node_pipe_dic=node_pipe_dic,
|
||||
all_node_series=all_node_series,
|
||||
top_group_ratio=0.3,
|
||||
top_pipe_num_max=80,
|
||||
top_pipe_num_min=10,
|
||||
candidate_pipe_input_initial=candidate_pipe,
|
||||
similarity_mode=similarity_mode,
|
||||
pressure_monitor=pressure_monitor,
|
||||
pressure_predict=pressure_predict,
|
||||
pressure_normal=pressure_normal,
|
||||
pressure_leak_all=None,
|
||||
flow_monitor=flow_monitor,
|
||||
flow_predict=flow_predict,
|
||||
flow_normal=flow_normal,
|
||||
flow_leak_all=None,
|
||||
timestep_list=timestep_list,
|
||||
max_flow=max_flow,
|
||||
group_basic_num=30,
|
||||
Top_sensor_num=min(5, len(pressure_ids)),
|
||||
if_gy=0,
|
||||
pressure_threshold=float(min_dpressure),
|
||||
leak_mag=float(burst_leakage),
|
||||
n_workers=max(1, int(n_workers)),
|
||||
stage_timing=stage_timing,
|
||||
try:
|
||||
(
|
||||
located_pipe,
|
||||
elapsed_seconds,
|
||||
simulation_times,
|
||||
_,
|
||||
similarity_series,
|
||||
exit_condition,
|
||||
final_candidates_csv,
|
||||
) = (
|
||||
DN_search_multi_simple_add_flow_count_new(
|
||||
wn=wn,
|
||||
wn_inp_path=str(inp_path),
|
||||
G0=G0,
|
||||
all_node=all_node,
|
||||
node_x=node_x,
|
||||
node_y=node_y,
|
||||
pipe_start_node_all=pipe_start_node_all,
|
||||
pipe_end_node_all=pipe_end_node_all,
|
||||
couple_node_length=couple_node_length,
|
||||
node_pipe_dic=node_pipe_dic,
|
||||
all_node_series=all_node_series,
|
||||
top_group_ratio=0.3,
|
||||
top_pipe_num_max=80,
|
||||
top_pipe_num_min=10,
|
||||
candidate_pipe_input_initial=candidate_pipe,
|
||||
similarity_mode=similarity_mode,
|
||||
pressure_monitor=pressure_monitor,
|
||||
pressure_predict=pressure_predict,
|
||||
pressure_normal=pressure_normal,
|
||||
pressure_leak_all=None,
|
||||
flow_monitor=flow_monitor,
|
||||
flow_predict=flow_predict,
|
||||
flow_normal=flow_normal,
|
||||
flow_leak_all=None,
|
||||
timestep_list=timestep_list,
|
||||
max_flow=max_flow,
|
||||
group_basic_num=30,
|
||||
Top_sensor_num=min(5, len(pressure_ids)),
|
||||
if_gy=0,
|
||||
pressure_threshold=float(min_dpressure),
|
||||
leak_mag=float(burst_leakage),
|
||||
n_workers=max(1, int(n_workers)),
|
||||
stage_timing=stage_timing,
|
||||
partition_on_full_graph=partition_on_full_graph,
|
||||
visualize_partition=visualize_partition,
|
||||
visualize_pause_seconds=visualize_pause_seconds,
|
||||
final_candidates_csv_path=final_candidates_csv_path,
|
||||
)
|
||||
)
|
||||
)
|
||||
except Exception as exc:
|
||||
logger.exception("Burst location algorithm execution failed.")
|
||||
raise RuntimeError(f"Failed to run burst location algorithm: {exc}") from exc
|
||||
|
||||
return {
|
||||
"located_pipe": located_pipe,
|
||||
@@ -221,6 +262,8 @@ def run_burst_location(
|
||||
"simulation_times": int(simulation_times),
|
||||
"top_candidates": _build_top_candidates(similarity_series),
|
||||
"similarity_mode": similarity_mode,
|
||||
"exit_condition": exit_condition,
|
||||
"final_candidates_csv": final_candidates_csv,
|
||||
"stage_timing_seconds": stage_timing,
|
||||
}
|
||||
|
||||
@@ -267,6 +310,11 @@ def _parse_args():
|
||||
default=DEFAULT_N_WORKERS,
|
||||
help="(可选)特征中心模拟进程数,默认 max(1, min(cpu_count()-1, 4))",
|
||||
)
|
||||
parser.add_argument(
|
||||
"--final-candidates-csv-path",
|
||||
default="temp/burst_location/final_round_candidates.csv",
|
||||
help="(可选)最后一轮候选管道明细 CSV 输出路径",
|
||||
)
|
||||
return parser.parse_args()
|
||||
|
||||
|
||||
@@ -284,6 +332,7 @@ def main():
|
||||
min_dpressure=args.min_dpressure,
|
||||
basic_pressure=args.basic_pressure,
|
||||
n_workers=args.n_workers,
|
||||
final_candidates_csv_path=args.final_candidates_csv_path,
|
||||
)
|
||||
print(json.dumps(result, ensure_ascii=False))
|
||||
|
||||
|
||||
Reference in New Issue
Block a user