From 2825766643ae580050418b72090e588abf2fc63f Mon Sep 17 00:00:00 2001 From: Alinson Xavier Date: Sun, 30 Apr 2017 13:51:14 -0400 Subject: [PATCH] Refactor infinity.c --- infinity/library/src/infinity.c | 102 ++++++++++++++++++-------------- multirow/include/multirow/cg.h | 12 ++-- multirow/src/cg.c | 25 ++++---- multirow/tests/cg-test.cpp | 74 ++++++++--------------- 4 files changed, 98 insertions(+), 115 deletions(-) diff --git a/infinity/library/src/infinity.c b/infinity/library/src/infinity.c index 36df6de..2e143b7 100644 --- a/infinity/library/src/infinity.c +++ b/infinity/library/src/infinity.c @@ -86,15 +86,17 @@ CLEANUP: } static int create_cut_from_lfree(const struct Tableau *tableau, - const struct RayMap *map, - const struct ConvLFreeSet *lfree, - struct Row *cut) + const struct TableauModelMap *map, + const struct MultiRowModel *model, + const struct ConvLFreeSet *lfree, + struct Row *cut) { int rval = 0; struct LP lp; int nvars = map->nvars; int nrows = tableau->nrows; + struct RayList *rays = &model->rays; rval = LP_open(&lp); abort_if(rval, "LP_open failed"); @@ -107,7 +109,7 @@ static int create_cut_from_lfree(const struct Tableau *tableau, for(int i = 0; i < nvars; i++) { double value; - const double *q = LFREE_get_ray(&map->rays, map->variable_to_ray[i]); + const double *q = LFREE_get_ray(rays, map->variable_to_ray[i]); if(ENABLE_LIFTING && tableau->column_types[map->indices[i]] == MILP_INTEGER) @@ -141,26 +143,28 @@ CLEANUP: return rval; } -static int filter_rays(const struct RayMap *map, - const struct Tableau *tableau, - struct MultiRowModel *model) +static int filter_model(const struct MultiRowModel *original_model, + struct MultiRowModel *filtered_model) { int rval = 0; - int nrows = tableau->nrows; - struct RayList *rays = &model->rays; + int nrows = original_model->nrows; + struct RayList *filtered_rays = &filtered_model->rays; + struct RayList *original_rays = &original_model->rays; + + memcpy(filtered_model->f, original_model->f, 2 * sizeof(double)); for(double norm_cutoff = 0.00; norm_cutoff <= 5.0; norm_cutoff += 0.1) { - rays->nrays = 0; + filtered_rays->nrays = 0; - for(int i = 0; i < map->rays.nrays; i++) + for(int i = 0; i < original_rays->nrays; i++) { int keep = 1; - double *r = LFREE_get_ray(&map->rays, i); + double *r = LFREE_get_ray(original_rays, i); - for(int j = 0; j < (rays->nrays); j++) + for(int j = 0; j < (filtered_rays->nrays); j++) { - double *q = LFREE_get_ray(&map->rays, j); + double *q = LFREE_get_ray(filtered_rays, j); double norm = 0; for(int k = 0; k < nrows; k++) @@ -173,13 +177,13 @@ static int filter_rays(const struct RayMap *map, } } - if(keep) LFREE_push_ray(rays, r); + if(keep) LFREE_push_ray(filtered_rays, r); } log_debug(" norm_cutoff=%8.2lf nrays=%8d\n", norm_cutoff, - model->rays.nrays); + filtered_model->rays.nrays); - if(rays->nrays < MAX_N_RAYS) break; + if(filtered_rays->nrays < MAX_N_RAYS) break; } CLEANUP: @@ -187,7 +191,7 @@ CLEANUP: } static int append_extra_rays(const struct Tableau *tableau, - struct RayList *rays) + struct MultiRowModel *model) { int rval = 0; int nrows = tableau->nrows; @@ -237,10 +241,10 @@ static int append_extra_rays(const struct Tableau *tableau, double scale; int found, index; - rval = CG_find_ray(rays, r, &found, &scale, &index); + rval = CG_find_ray(&model->rays, r, &found, &scale, &index); abort_if(rval, "CG_find_ray failed"); - if(!found) LFREE_push_ray(rays, r); + if(!found) LFREE_push_ray(&model->rays, r); } CLEANUP: @@ -299,30 +303,31 @@ CLEANUP: return rval; } -static int extract_model_from_tableau(const struct Tableau *tableau, - struct MultiRowModel *model, - struct RayMap *map) +static int extract_models(const struct Tableau *tableau, + struct MultiRowModel *original_model, + struct MultiRowModel *filtered_model, + struct TableauModelMap *original_map) { int rval = 0; - rval = CG_extract_f_from_tableau(tableau, model->f); + rval = CG_extract_f_from_tableau(tableau, original_model->f); abort_if(rval, "CG_extract_f_from_tableau failed"); - rval = CG_extract_rays_from_tableau(tableau, map); + rval = CG_extract_model(tableau, original_map, original_model); abort_if(rval, "CG_extract_rays_from_rows failed"); - rval = filter_rays(map, tableau, model); - abort_if(rval, "filter_rays failed"); + rval = filter_model(original_model, filtered_model); + abort_if(rval, "filter_model failed"); if(ENABLE_LIFTING) { - rval = append_extra_rays(tableau, &model->rays); + rval = append_extra_rays(tableau, filtered_model); abort_if(rval, "append_extra_rays failed"); } if(tableau->nrows == 2) { - rval = sort_rays_by_angle(&model->rays); + rval = sort_rays_by_angle(&filtered_model->rays); abort_if(rval, "sort_rays_by_angle failed"); } @@ -335,34 +340,39 @@ CLEANUP: int INFINITY_generate_cut(const struct Tableau *tableau, struct Row *cut) { int rval = 0; - int max_nrays = CG_total_nz(tableau); + int max_nrays = CG_total_nz(tableau) + 100; - struct RayMap map; - struct MultiRowModel model; + struct MultiRowModel original_model; + struct MultiRowModel filtered_model; + struct TableauModelMap original_map; struct ConvLFreeSet lfree; - rval = CG_init_model(&model, tableau->nrows, max_nrays + 100); + rval = CG_init_model(&original_model, tableau->nrows, max_nrays); + abort_if(rval, "CG_init_model failed"); + + rval = CG_init_model(&filtered_model, tableau->nrows, max_nrays); abort_if(rval, "CG_init_model failed"); - rval = CG_init_ray_map(&map, max_nrays, tableau->nrows); - abort_if(rval, "CG_init_ray_map failed"); + rval = CG_init_map(&original_map, max_nrays, tableau->nrows); + abort_if(rval, "CG_init_map failed"); - rval = extract_model_from_tableau(tableau, &model, &map); - abort_if(rval, "extract_model_from_tableau failed"); + rval = extract_models(tableau, &original_model, &filtered_model, + &original_map); + abort_if(rval, "extract_models failed"); - if(model.rays.nrays < 3) + if(filtered_model.rays.nrays < 3) { rval = ERR_NO_CUT; goto CLEANUP; } - rval = LFREE_init_conv(&lfree, tableau->nrows, model.rays.nrays); + rval = LFREE_init_conv(&lfree, tableau->nrows, filtered_model.rays.nrays); abort_if(rval, "LFREE_init_conv failed"); if(tableau->nrows == 2) - rval = INFINITY_2D_generate_lfree(&model, &lfree); + rval = INFINITY_2D_generate_lfree(&filtered_model, &lfree); else - rval = INFINITY_ND_generate_lfree(&model, &lfree); + rval = INFINITY_ND_generate_lfree(&filtered_model, &lfree); if(rval) { @@ -372,17 +382,19 @@ int INFINITY_generate_cut(const struct Tableau *tableau, struct Row *cut) if(SHOULD_DUMP_CUTS) { - rval = dump_cut(&model, &lfree); + rval = dump_cut(&filtered_model, &lfree); abort_if(rval, "dump_cut failed"); } - rval = create_cut_from_lfree(tableau, &map, &lfree, cut); + rval = create_cut_from_lfree(tableau, &original_map, &original_model, + &lfree, cut); abort_if(rval, "create_cut_from_lfree failed"); CLEANUP: LFREE_free_conv(&lfree); - CG_free_model(&model); - CG_free_ray_map(&map); + CG_free_model(&original_model); + CG_free_model(&filtered_model); + CG_free_map(&original_map); return rval; } diff --git a/multirow/include/multirow/cg.h b/multirow/include/multirow/cg.h index 8a74c5c..c8bfe86 100644 --- a/multirow/include/multirow/cg.h +++ b/multirow/include/multirow/cg.h @@ -47,9 +47,8 @@ struct Tableau char *column_types; }; -struct RayMap +struct TableauModelMap { - struct RayList rays; int *variable_to_ray; double *ray_scale; int *indices; @@ -84,8 +83,9 @@ int CG_set_integral_solution(struct CG *cg, double *valid_solution); int CG_set_basic_solution(struct CG *cg, double *basic_solution); -int CG_extract_rays_from_tableau(const struct Tableau *tableau, - struct RayMap *map); +int CG_extract_model(const struct Tableau *tableau, + struct TableauModelMap *map, + struct MultiRowModel *model); int CG_boost_variable(int var, double factor, @@ -102,9 +102,9 @@ int CG_find_ray(const struct RayList *rays, double *scale, int *index); -int CG_init_ray_map(struct RayMap *map, int max_nrays, int nrows); +int CG_init_map(struct TableauModelMap *map, int max_nrays, int nrows); -void CG_free_ray_map(struct RayMap *map); +void CG_free_map(struct TableauModelMap *map); int CG_extract_f_from_tableau(const struct Tableau *tableau, double *f); diff --git a/multirow/src/cg.c b/multirow/src/cg.c index e72f76e..7266be5 100644 --- a/multirow/src/cg.c +++ b/multirow/src/cg.c @@ -440,8 +440,9 @@ CLEANUP: return 0; } -int CG_extract_rays_from_tableau(const struct Tableau *tableau, - struct RayMap *map) +int CG_extract_model(const struct Tableau *tableau, + struct TableauModelMap *map, + struct MultiRowModel *model) { int rval = 0; @@ -463,7 +464,7 @@ int CG_extract_rays_from_tableau(const struct Tableau *tableau, while (1) { - double *r = LFREE_get_ray(&map->rays, map->rays.nrays); + double *r = LFREE_get_ray(&model->rays, model->rays.nrays); int idx_min = INT_MAX; @@ -501,19 +502,19 @@ int CG_extract_rays_from_tableau(const struct Tableau *tableau, for (int j = 0; j < nrows; j++) log_verbose(" r[%d] = %.12lf\n", j, r[j]); - rval = CG_find_ray(&map->rays, r, &found, &scale, &ray_index); + rval = CG_find_ray(&model->rays, r, &found, &scale, &ray_index); abort_if(rval, "CG_find_ray failed"); if (!found) { log_verbose(" ray is new\n"); scale = 1.0; - ray_index = map->rays.nrays++; + ray_index = model->rays.nrays++; } else { log_verbose(" ray equals:\n"); - double *q = LFREE_get_ray(&map->rays, ray_index); + double *q = LFREE_get_ray(&model->rays, ray_index); for (int j = 0; j < nrows; j++) log_verbose(" r[%d] = %.12lf\n", j, q[j]); } @@ -526,9 +527,9 @@ int CG_extract_rays_from_tableau(const struct Tableau *tableau, NEXT_RAY:; } - for (int j = 0; j < map->rays.nrays; j++) + for (int j = 0; j < model->rays.nrays; j++) { - double *r = LFREE_get_ray(&map->rays, j); + double *r = LFREE_get_ray(&model->rays, j); double max_scale = 0.0; for (int k = 0; k < map->nvars; k++) @@ -1045,7 +1046,7 @@ CLEANUP: return rval; } -int CG_init_ray_map(struct RayMap *map, int max_nrays, int nrows) +int CG_init_map(struct TableauModelMap *map, int max_nrays, int nrows) { int rval = 0; @@ -1056,20 +1057,16 @@ int CG_init_ray_map(struct RayMap *map, int max_nrays, int nrows) abort_if(!map->indices, "could not allocate indices"); abort_if(!map->ray_scale, "could not allocate ray_scale"); - rval = LFREE_init_ray_list(&map->rays, nrows, max_nrays); - abort_if(rval, "LFREE_init_ray_list failed"); - CLEANUP: return rval; } -void CG_free_ray_map(struct RayMap *map) +void CG_free_map(struct TableauModelMap *map) { if(!map) return; free(map->variable_to_ray); free(map->indices); free(map->ray_scale); - LFREE_free_ray_list(&map->rays); } int CG_extract_f_from_tableau(const struct Tableau *tableau, double *f) diff --git a/multirow/tests/cg-test.cpp b/multirow/tests/cg-test.cpp index 3cce9bf..6671e75 100644 --- a/multirow/tests/cg-test.cpp +++ b/multirow/tests/cg-test.cpp @@ -113,75 +113,49 @@ TEST(CGTest, extract_rays_from_rows_test) char column_types[16] = {0}; double pi1[] = { 1.0, 1.0, 1.0, 2.0, 1.0 }; int indices1[] = { 1, 7, 8, 12, 14 }; - struct Row row1 = - { - .nz = 5, - .head = 1, - .pi_zero = 1.0, - .pi = pi1, - .indices = indices1 - }; + struct Row row1 = {.nz = 5, .head = 1, .pi_zero = 1.0, .pi = pi1, .indices = indices1}; double pi2[] = { 1.0, 1.0, 2.0, 1.0, 1.0, 1.0 }; int indices2[] = { 5, 8, 12, 13, 14, 16 }; - struct Row row2 = - { - .nz = 6, - .head = 13, - .pi_zero = 1.0, - .pi = pi2, - .indices = indices2 - }; - + struct Row row2 = {.nz = 6, .head = 13, .pi_zero = 1.0, .pi = pi2, .indices = indices2}; + double pi3[] = { 1.0, 1.0, 1.0, 1.0 }; int indices3[] = { 3, 7, 10, 16 }; - struct Row row3 = - { - .nz = 4, - .head = 7, - .pi_zero = 1.0, - .pi = pi3, - .indices = indices3 - }; - + struct Row row3 = {.nz = 4, .head = 7, .pi_zero = 1.0, .pi = pi3, .indices = indices3}; + struct Row *rows[] = { &row1, &row2, &row3 }; - struct Tableau tableau = - { - .ncols = 16, - .nrows = 3, - .rows = rows, - .column_types = column_types - }; + struct Tableau tableau = {.ncols = 16, .nrows = 3, .rows = rows, .column_types = column_types}; int indices[1000]; int variable_to_ray[1000]; double ray_scale[1000]; - struct RayList rays; - LFREE_init_ray_list(&rays, 3, 1000); - struct RayMap map = {rays, variable_to_ray, ray_scale, indices, 0}; + struct TableauModelMap map = {variable_to_ray, ray_scale, indices, 0}; + + struct MultiRowModel model; + CG_init_model(&model, 3, 1000); - rval = CG_extract_rays_from_tableau(&tableau, &map); + rval = CG_extract_model(&tableau, &map, &model); abort_if(rval, "CG_extract_rays_from_rows failed"); - EXPECT_EQ(map.rays.nrays, 4); EXPECT_EQ(map.nvars, 7); - EXPECT_DOUBLE_EQ(rays.values[0], 0.0); - EXPECT_DOUBLE_EQ(rays.values[1], 0.0); - EXPECT_DOUBLE_EQ(rays.values[2], -1.0); + EXPECT_EQ(model.rays.nrays, 4); + EXPECT_DOUBLE_EQ(model.rays.values[0], 0.0); + EXPECT_DOUBLE_EQ(model.rays.values[1], 0.0); + EXPECT_DOUBLE_EQ(model.rays.values[2], -1.0); - EXPECT_DOUBLE_EQ(rays.values[3], 0.0); - EXPECT_DOUBLE_EQ(rays.values[4], -1.0); - EXPECT_DOUBLE_EQ(rays.values[5], 0.0); + EXPECT_DOUBLE_EQ(model.rays.values[3], 0.0); + EXPECT_DOUBLE_EQ(model.rays.values[4], -1.0); + EXPECT_DOUBLE_EQ(model.rays.values[5], 0.0); - EXPECT_DOUBLE_EQ(rays.values[6], -2.0); - EXPECT_DOUBLE_EQ(rays.values[7], -2.0); - EXPECT_DOUBLE_EQ(rays.values[8], 0.0); + EXPECT_DOUBLE_EQ(model.rays.values[6], -2.0); + EXPECT_DOUBLE_EQ(model.rays.values[7], -2.0); + EXPECT_DOUBLE_EQ(model.rays.values[8], 0.0); - EXPECT_DOUBLE_EQ(rays.values[ 9], 0.0); - EXPECT_DOUBLE_EQ(rays.values[10], -1.0); - EXPECT_DOUBLE_EQ(rays.values[11], -1.0); + EXPECT_DOUBLE_EQ(model.rays.values[ 9], 0.0); + EXPECT_DOUBLE_EQ(model.rays.values[10], -1.0); + EXPECT_DOUBLE_EQ(model.rays.values[11], -1.0); EXPECT_EQ(indices[0], 3); EXPECT_EQ(indices[1], 5);