genmodel 0.0.46 → 0.0.47

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (3) hide show
  1. checksums.yaml +8 -8
  2. data/ext/Genmodel/GenModelCplex.cpp +83 -55
  3. metadata +1 -1
checksums.yaml CHANGED
@@ -1,15 +1,15 @@
1
1
  ---
2
2
  !binary "U0hBMQ==":
3
3
  metadata.gz: !binary |-
4
- Mjc5YjRiNDdhMjkyODU3NzZlMDdmODVjYWM5MjNjZWFlNWQwNDMxMw==
4
+ NjVhZWRiNjNiNjE5ZWE0ZWVmYzg5MzkwMmM4YjgzOGFjYzMyMTQyOQ==
5
5
  data.tar.gz: !binary |-
6
- ODMxYjUxNThkMzkzNWRkNjdmOTk2ZDE4NzUxMjJjMmFiZjgzMzU1MQ==
6
+ NDA0YzRiYjVhNjVmZTMyNzA3NjNmNzk5Nzk3NmViMzJmNDcyYzZkNQ==
7
7
  SHA512:
8
8
  metadata.gz: !binary |-
9
- NWFlMmYyMDhmYTY2N2QxZDczNTQ5MjgxZjFkODQwOWEwMGI2ODJhMzNjYjkx
10
- MDFlZTkzNTczYzYzYWY1MDI0YTM4ZGRkNWJlZTAzM2NhNjg3NmUwY2I2YmZm
11
- MGUyMDg3MjYzODJmMGY1YjY5MTY5MWYwYWVkMmEyMTNhNGVlMjY=
9
+ NjliNWYxNGM3NzgxZGM2ZDUzZDA4NWZiNTEyY2EwOGJmNmNjYmY3YjUzN2I2
10
+ MjUwM2Q5M2RjODJjZGU0NzU2MTFjMzlhOTkwODBjZjhhZjJmNjg5ZTc5NzEy
11
+ ZWRmYTM5YjgwNTczNzk5ZTI2OGU0YTM1NjJkNmUyNGNmNzA0MWI=
12
12
  data.tar.gz: !binary |-
13
- MzMxMGZiOGU4MzZiNTIwYmVhOTBjYTVkNDYxZWNiZDQ2NDEwYjc2MmIzZjI4
14
- OWViZTM2ZWE1YzBkNGJmZGMxOWRiMTI2MWRiYTAwOTMxZDQ2Y2U0YmVhODgx
15
- MTA5NTU5YjFmYWM4Zjg2NjdjNTM1NzVkZTA3ZGEwMGIzNjRlYmU=
13
+ ZWJiYTU4ZDdjZGJjODhjNDM2Mzk5MjljMDFlNWUyYzY5Njk4YjAyMmZiYWU2
14
+ MDE4OWJlYWRmNTU3OWFmODlkZDY1YjhiZWM4ZWE5ZWU5MDNiZjIyYmYzMTgw
15
+ NjU0NDAxNDUyYjBmNmRlODUyMDA1ZDlmNTYyNTE4YTk1ZjI5NDI=
@@ -316,36 +316,18 @@ long GenModelCplex::CreateModel()
316
316
  }
317
317
  status = CPXXnewrows (d->env, d->lp, nr, d->lrhs, d->sense, d->urhs, d->rname);
318
318
  if ( status )
319
- {
320
- char errmsg[1024];
321
- fprintf (stderr, "Could not create new rows.\n");
322
- CPXXgeterrorstring (d->env, status, errmsg);
323
- fprintf (stderr, "%s", errmsg);
324
- return 1;
325
- }
326
- //else
327
- //printf("Row added!\n");
328
-
319
+ return ThrowError(getcplexerror(d->env, status)+string(". ")+string("CreateModel() : Could not create new rows"));
320
+
329
321
  if(boolParam.count("mip") > 0 && boolParam["mip"])
330
322
  status = CPXXnewcols (d->env, d->lp, nc, d->obj, d->lb, d->ub, d->type, d->cname);
331
323
  else
332
324
  status = CPXXnewcols (d->env, d->lp, nc, d->obj, d->lb, d->ub, NULL, NULL);
333
325
  if ( status )
334
- {
335
- char errmsg[1024];
336
- fprintf (stderr, "Could not create new cols.\n");
337
- CPXXgeterrorstring (d->env, status, errmsg);
338
- fprintf (stderr, "%s", errmsg);
339
- return 1;
340
- }
341
- //status = CPXXnewcols (env, lp, nc, obj, lb, ub, NULL, colname);
342
- if ( status )
343
- return 1;
344
- //else
345
- //printf("Col added!\n");
326
+ return ThrowError(getcplexerror(d->env, status)+string(". ")+string("CreateModel() : Could not create new cols"));
327
+
346
328
  status = CPXXchgcoeflist (d->env, d->lp, nz, d->mat_r, d->mat_c, d->mat_v);
347
329
  if ( status )
348
- return 1;
330
+ return ThrowError(getcplexerror(d->env, status)+string(". ")+string("CreateModel() : Could not set coefficients"));
349
331
 
350
332
  vector<long>::iterator iti;
351
333
  vector<long>::iterator itj = vars.qj.begin();
@@ -577,7 +559,6 @@ string SolverInfo::inspect() const
577
559
 
578
560
  string SolverInfo::to_s() const
579
561
  {
580
- char tmp[10000];
581
562
  string _cpx_results = cpx_results;
582
563
  string _cpx_warning = cpx_warning;
583
564
  string _cpx_error = cpx_error;
@@ -591,8 +572,12 @@ string SolverInfo::to_s() const
591
572
  pos = 0;
592
573
  while((pos = _cpx_log.find("\n", pos)) != std::string::npos) { _cpx_log.replace(pos, 1, "\\n"); pos += 2; }
593
574
 
594
- snprintf(tmp, 10000,
575
+ size_t buffer_size = 10000+cpx_results.size()+_cpx_warning.size()+_cpx_error.size()+_cpx_log.size();
576
+ char tmp[buffer_size];
577
+
578
+ snprintf(tmp, buffer_size,
595
579
  "{\n"
580
+ "\t\"status_str\" : \"%s\",\n"
596
581
  "\t\"relative_gap\" : \"%f\",\n"
597
582
  "\t\"upper_bound\" : \"%f\",\n"
598
583
  "\t\"lower_bound\" : \"%f\",\n"
@@ -617,17 +602,16 @@ string SolverInfo::to_s() const
617
602
  "\t\"nb_user_cuts\" : %lu,\n"
618
603
  "\t\"nb_lazy_cuts\" : %lu,\n"
619
604
  "\t\"nb_soln_pool_cuts\" : %lu,\n"
605
+ "\t\"cpx_error\" : \"%s\",\n"
620
606
  "\t\"cpx_results\" : \"%s\",\n"
621
607
  "\t\"cpx_warning\" : \"%s\",\n"
622
- "\t\"cpx_error\" : \"%s\",\n"
623
- "\t\"cpx_log\" : \"%s\",\n"
624
- "\t\"status_str\" : \"%s\""
608
+ "\t\"cpx_log\" : \"%s\"\n"
625
609
  "}\n",
626
- relative_gap,upper_bound,lower_bound,cutoff,nb_node_solved,nb_node_left,nb_threads,nb_iters,nb_solutions,nb_clique_cuts,nb_cover_cuts,nb_disjcut_cuts,
610
+ status_str.c_str(),relative_gap,upper_bound,lower_bound,cutoff,nb_node_solved,nb_node_left,nb_threads,nb_iters,nb_solutions,nb_clique_cuts,nb_cover_cuts,nb_disjcut_cuts,
627
611
  nb_flow_cover_cuts,nb_flow_path_cuts,nb_fractionnal_cuts,nb_gub_cover_cuts,nb_implied_bound_cuts,nb_lift_project_cuts,nb_flow_mc_flow_cuts,nb_flow_mir_cuts,
628
- nb_zero_half_cuts,nb_user_cuts,nb_lazy_cuts,nb_soln_pool_cuts,_cpx_results.c_str(),_cpx_warning.c_str(),_cpx_error.c_str(),_cpx_log.c_str(), status_str.c_str()
612
+ nb_zero_half_cuts,nb_user_cuts,nb_lazy_cuts,nb_soln_pool_cuts,_cpx_error.c_str(),_cpx_results.c_str(),_cpx_warning.c_str(),_cpx_log.c_str()
629
613
  );
630
-
614
+
631
615
  return string(tmp);
632
616
  }
633
617
 
@@ -656,13 +640,16 @@ SolverInfo GenModelCplex::GetSolverInfo()
656
640
 
657
641
  int mip_cb(CPXCENVptr env, void *cbdata, int wherefrom, void *cbhandle)
658
642
  {
659
- printf("Callback called\n");
660
643
  GenModelCplex* pgm = static_cast<GenModelCplex*>(cbhandle);
661
644
  CplexData* d = static_cast<CplexData*>(pgm->solverdata);
662
645
 
663
646
  vector<vector<double> > solutions;
664
647
  vector<double> solution_objvals;
665
648
 
649
+ size_t nb_clique_cuts = 0, nb_cover_cuts = 0, nb_disjcut_cuts = 0, nb_flow_cover_cuts = 0, nb_flow_path_cuts = 0, nb_fractionnal_cuts = 0, nb_gub_cover_cuts = 0,
650
+ nb_implied_bound_cuts = 0, nb_lift_project_cuts = 0, nb_flow_mc_flow_cuts = 0, nb_flow_mir_cuts = 0, nb_zero_half_cuts = 0, nb_user_cuts = 0,
651
+ nb_lazy_cuts = 0, nb_soln_pool_cuts = 0;
652
+
666
653
  if(pgm->boolParam.count("maximize") > 0 && pgm->boolParam["maximize"])
667
654
  {
668
655
  CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_BEST_INTEGER, &(d->solver_info.lower_bound));
@@ -680,28 +667,60 @@ int mip_cb(CPXCENVptr env, void *cbdata, int wherefrom, void *cbhandle)
680
667
  CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_MIP_ITERATIONS_LONG, &(d->solver_info.nb_iters));
681
668
  CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_USER_THREADS, &(d->solver_info.nb_threads));
682
669
 
683
- CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_CLIQUE_COUNT, &(d->solver_info.nb_clique_cuts));
684
- CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_COVER_COUNT, &(d->solver_info.nb_cover_cuts));
685
- CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_DISJCUT_COUNT, &(d->solver_info.nb_disjcut_cuts));
686
- CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_FLOWCOVER_COUNT, &(d->solver_info.nb_flow_cover_cuts));
687
- CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_FLOWPATH_COUNT, &(d->solver_info.nb_flow_path_cuts));
688
- CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_FRACCUT_COUNT, &(d->solver_info.nb_fractionnal_cuts));
689
- CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_GUBCOVER_COUNT, &(d->solver_info.nb_gub_cover_cuts));
690
- CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_IMPLBD_COUNT, &(d->solver_info.nb_implied_bound_cuts));
691
- CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_LANDPCUT_COUNT, &(d->solver_info.nb_lift_project_cuts));
692
- CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_MCFCUT_COUNT, &(d->solver_info.nb_flow_mc_flow_cuts));
693
- CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_MIRCUT_COUNT, &(d->solver_info.nb_flow_mir_cuts));
694
- CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_ZEROHALFCUT_COUNT, &(d->solver_info.nb_zero_half_cuts));
695
- CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_USERCUT_COUNT, &(d->solver_info.nb_user_cuts));
696
- CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_TABLECUT_COUNT, &(d->solver_info.nb_lazy_cuts));
697
- CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_SOLNPOOLCUT_COUNT, &(d->solver_info.nb_soln_pool_cuts));
670
+ CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_CLIQUE_COUNT, &nb_clique_cuts);
671
+ CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_COVER_COUNT, &nb_cover_cuts);
672
+ CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_DISJCUT_COUNT, &nb_disjcut_cuts);
673
+ CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_FLOWCOVER_COUNT, &nb_flow_cover_cuts);
674
+ CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_FLOWPATH_COUNT, &nb_flow_path_cuts);
675
+ CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_FRACCUT_COUNT, &nb_fractionnal_cuts);
676
+ CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_GUBCOVER_COUNT, &nb_gub_cover_cuts);
677
+ CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_IMPLBD_COUNT, &nb_implied_bound_cuts);
678
+ CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_LANDPCUT_COUNT, &nb_lift_project_cuts);
679
+ CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_MCFCUT_COUNT, &nb_flow_mc_flow_cuts);
680
+ CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_MIRCUT_COUNT, &nb_flow_mir_cuts);
681
+ CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_ZEROHALFCUT_COUNT, &nb_zero_half_cuts);
682
+ CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_USERCUT_COUNT, &nb_user_cuts);
683
+ CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_TABLECUT_COUNT, &nb_lazy_cuts);
684
+ CPXXgetcallbackinfo(d->env, cbdata, wherefrom, CPX_CALLBACK_INFO_SOLNPOOLCUT_COUNT, &nb_soln_pool_cuts);
685
+
686
+ d->solver_info.nb_clique_cuts += nb_clique_cuts;
687
+ d->solver_info.nb_cover_cuts += nb_cover_cuts;
688
+ d->solver_info.nb_disjcut_cuts += nb_disjcut_cuts;
689
+ d->solver_info.nb_flow_cover_cuts += nb_flow_cover_cuts;
690
+ d->solver_info.nb_flow_path_cuts += nb_flow_path_cuts;
691
+ d->solver_info.nb_fractionnal_cuts += nb_fractionnal_cuts;
692
+ d->solver_info.nb_gub_cover_cuts += nb_gub_cover_cuts;
693
+ d->solver_info.nb_implied_bound_cuts += nb_implied_bound_cuts;
694
+ d->solver_info.nb_lift_project_cuts += nb_lift_project_cuts;
695
+ d->solver_info.nb_flow_mc_flow_cuts += nb_flow_mc_flow_cuts;
696
+ d->solver_info.nb_flow_mir_cuts += nb_flow_mir_cuts;
697
+ d->solver_info.nb_zero_half_cuts += nb_zero_half_cuts;
698
+ d->solver_info.nb_user_cuts += nb_user_cuts;
699
+ d->solver_info.nb_lazy_cuts += nb_lazy_cuts;
700
+ d->solver_info.nb_soln_pool_cuts += nb_soln_pool_cuts;
701
+
702
+ //d->solver_info.nb_solutions = CPXXgetsolnpoolnumsolns(d->env, d->lp);
698
703
 
699
704
  if(d->stop_solver)
700
705
  return 1;
701
-
702
- d->solver_info.nb_solutions = CPXXgetsolnpoolnumsolns(d->env, d->lp);
703
706
 
704
- return d->original_mip_cb(env, cbdata, wherefrom, d->original_handle);
707
+ return 0;
708
+ }
709
+
710
+ int sol_cb (CPXCENVptr env, void *cbdata, int wherefrom, void *cbhandle, double objval, double *x, int *isfeas_p, int *useraction_p)
711
+ {
712
+ GenModelCplex* pgm = static_cast<GenModelCplex*>(cbhandle);
713
+ CplexData* d = static_cast<CplexData*>(pgm->solverdata);
714
+ ++(d->solver_info.nb_solutions);
715
+ *isfeas_p = 1;
716
+ *useraction_p = 0;
717
+ return 0;
718
+ }
719
+
720
+ int cut_cb(CPXCENVptr env, void *cbdata, int wherefrom, void *cbhandle, int *useraction_p)
721
+ {
722
+ *useraction_p = CPX_CALLBACK_DEFAULT;
723
+ return mip_cb(env, cbdata, wherefrom, cbhandle);
705
724
  }
706
725
 
707
726
  void msg_function(void* cbhandle, const char* msg)
@@ -762,15 +781,24 @@ long GenModelCplex::Init(string name)
762
781
 
763
782
  if(boolParam.count("fill_solver_info") > 0)
764
783
  {
765
- printf("solver_info ON\n");
766
- /*status = CPXXgetmipcallbackfunc(d->env, &(d->original_mip_cb), &(d->original_handle));
767
- if (status)
768
- return ThrowError(getcplexerror(d->env, status)+string(". ")+string("Failure to get the default mip callback function"));
784
+ //printf("solver_info ON\n");
785
+ // status = CPXXgetmipcallbackfunc(d->env, &(d->original_mip_cb), &(d->original_handle));
786
+ // if (status)
787
+ // return ThrowError(getcplexerror(d->env, status)+string(". ")+string("Failure to get the default mip callback function"));
788
+
789
+ status = CPXXsetusercutcallbackfunc(d->env, cut_cb, this);
790
+ if (status)
791
+ return ThrowError(getcplexerror(d->env, status)+string(". ")+string("Failure to set the cut callback function"));
792
+
769
793
 
770
794
  status = CPXXsetmipcallbackfunc(d->env, mip_cb, this);
771
795
  if (status)
772
796
  return ThrowError(getcplexerror(d->env, status)+string(". ")+string("Failure to set the mip callback function"));
773
- */
797
+
798
+ status = CPXXsetincumbentcallbackfunc(d->env, sol_cb, this);
799
+ if (status)
800
+ return ThrowError(getcplexerror(d->env, status)+string(". ")+string("Failure to set the solution callback function"));
801
+
774
802
 
775
803
  CPXCHANNELptr cpxresults, cpxwarning, cpxerror, cpxlog;
776
804
  status = CPXXgetchannels(d->env, &cpxresults, &cpxwarning, &cpxerror, &cpxlog);
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: genmodel
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.46
4
+ version: 0.0.47
5
5
  platform: ruby
6
6
  authors:
7
7
  - Mathieu Bouchard