Open Hodapp87 opened 8 years ago
I have reproduced the bug. I suspect that it has something to do with the unfortunate fact that glpk is not thread safe, see https://github.com/albertoruiz/hmatrix/issues/32. Perhaps the first call in seq
is not complete when the second call is done. I hope there are simpler use cases in which this glpk wrapper is useful, but this behavior is a very bad thing and we cannot trust the module.
I was implementing something more complicated with hmatrix & hmatrix-glpk and I ran into issues with the GLPK calls labeling something unexpectedly as
Infeasible
orUnbounded
. I added trace statements to dump the input data (which was just two lists of Doubles), and if I ran this same data on its own in another context (like ghci), it would invariably returnOptimal
. This continued even to the point where I encoded the input viaData.Binary
and then decoded it elsewhere and evaluated it manually there with exactly the same function.Here is the basic code that causes the issue. I'm sorry it's convoluted - I can't seem to reduce it further without failing to demonstrate the bug, and it's a heavily-pruned version of the algorithm that produced the problem:
This is also available with a cabal & stack file at https://github.com/Hodapp87/hmatrix-test. I observe the when running
stack build && stack exec test
:test: Failed at try B: Unbounded, obj=[2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0,2.0]
I do not observe this same behavior with ghci.
Take a look at a few things around line 19: It's solving over 25 variables, it has a constraint that they all sum to 1, they're all bounded between 0 and 1. In the output above,
obj
is coefficients for the objective function to maximize. It can't be unbounded - it's just a convex sum over a bunch of 2s, its maximum is 2. Evaluating in ghci with the same code andobj
value readily shows this:Furthermore: in lines 24 and 28,
tryA
andtryB
have identical inputs, yet they produce different results if I force evaluation of both (the error is never produced in evaluatingtryA
). If I replaceseq tryA tryB
with justtryA
ortryB
, the bug does not appear.So, why are two identical calls producing different results, one of which is incorrect?