59 lines
2.0 KiB
C
59 lines
2.0 KiB
C
#include <c_DijkstraAllPairsSP.h>
|
|
|
|
c_err_t c_DijkstraAllPairsSP_Init(c_DijkstraAllPairsSP_t* self, c_EdgeWeightedDigraph_t* graph, c_Allocator_t* allocator) {
|
|
if (!self || !graph) return C_ERR_PARAM;
|
|
|
|
self->allocator = allocator ? *allocator : c_DefaultAllocator;
|
|
self->V = graph->V;
|
|
self->sp_matrix = NULL;
|
|
|
|
if (self->V == 0) return C_SUCCESS;
|
|
|
|
/* 1. Allocate an array of DijkstraSP structures */
|
|
self->sp_matrix = (c_DijkstraSP_t*)c_Allocator_Calloc(
|
|
&self->allocator,
|
|
self->V,
|
|
sizeof(c_DijkstraSP_t)
|
|
);
|
|
if (!self->sp_matrix) return C_ERR_NOMEM;
|
|
|
|
/* 2. Run a full single-source Dijkstra search engine out from each vertex */
|
|
for (c_size_t v = 0; v < self->V; ++v) {
|
|
c_err_t err = c_DijkstraSP_Init(&self->sp_matrix[v], graph, v, allocator);
|
|
|
|
if (err != C_SUCCESS) {
|
|
/* Atomic Rollback: Destroy previously allocated instances to prevent OOM memory leaks */
|
|
for (c_size_t i = 0; i < v; ++i) {
|
|
c_DijkstraSP_Destroy(&self->sp_matrix[i]);
|
|
}
|
|
c_Allocator_Free(&self->allocator, self->sp_matrix);
|
|
self->sp_matrix = NULL;
|
|
self->V = 0;
|
|
return err;
|
|
}
|
|
}
|
|
|
|
return C_SUCCESS;
|
|
}
|
|
|
|
void c_DijkstraAllPairsSP_Destroy(c_DijkstraAllPairsSP_t* self) {
|
|
if (!self) return;
|
|
|
|
if (self->sp_matrix) {
|
|
/* Safely deallocate every single active search instance */
|
|
for (c_size_t i = 0; i < self->V; ++i) {
|
|
c_DijkstraSP_Destroy(&self->sp_matrix[i]);
|
|
}
|
|
c_Allocator_Free(&self->allocator, self->sp_matrix);
|
|
self->sp_matrix = NULL;
|
|
}
|
|
self->V = 0;
|
|
}
|
|
|
|
c_err_t c_DijkstraAllPairsSP_Path(c_DijkstraAllPairsSP_t* self, c_size_t u, c_size_t v, c_VertexIdList_t* out_path) {
|
|
if (!self || !self->sp_matrix || u >= self->V || v >= self->V || !out_path) return C_ERR_PARAM;
|
|
|
|
/* Safely delegate extraction to the underlying single-source engine */
|
|
return c_DijkstraSP_PathTo(&self->sp_matrix[u], v, out_path);
|
|
}
|