How to round down coefficients in a constraint in Julia/JuMP?

Hi, I am new here. I don’t know how to round down coefficients in my constraints. (only coefficients in this constraint. I don’t want to round down elements in the given array)


Anyone can help me? Thanks in advance!

1 Like

I have a similar question. I have no idea how to drop some coefficients with real small absolute value.

Anyone know if this can be implemented in Julia/JuMP?

@Shor You can achieve this with map_coefficients or map_coefficients_inplace:

julia> using JuMP

julia> model = Model()
A JuMP Model
Feasibility problem with:
Variables: 0
Model mode: AUTOMATIC
CachingOptimizer state: NO_OPTIMIZER
Solver name: No optimizer attached.

julia> @variable(model, x[1:2])
2-element Array{VariableRef,1}:
 x[1]
 x[2]

julia> A = rand(2, 2)
2×2 Array{Float64,2}:
b 0.842142  0.76944  
 0.893902  0.0591743

julia> b = rand(2)
2-element Array{Float64,1}:
 0.3355544786560043
 0.6001568619069537

julia> func = sum((A * x + b).^2)
1.5082646220201505 x[1]² + 1.4017481381221626 x[2]*x[1] + 0.5955394597878509 x[2]² + 1.638132146198787 x[1] + 0.5874057892258127 x[2] + 0.47278506704010514

julia> map_coefficients_inplace!(a -> round(a, digits=2), func)
1.51 x[1]² + 1.4 x[2]*x[1] + 0.6 x[2]² + 1.64 x[1] + 0.59 x[2] + 0.47

julia> @objective(model, Min, func)
1.51 x[1]² + 1.4 x[2]*x[1] + 0.6 x[2]² + 1.64 x[1] + 0.59 x[2] + 0.47

julia> print(model)
Min 1.51 x[1]² + 1.4 x[2]*x[1] + 0.6 x[2]² + 1.64 x[1] + 0.59 x[2] + 0.47
Subject to

@wenqi_kou To drop coefficients of small values you can do

julia> func = 1e-7x[1] + x[2]
1.0e-7 x[1] + x[2]

julia> map_coefficients_inplace!(a -> abs(a) < 1e-6 ? zero(a) : a, func)
0 x[1] + x[2]

julia> drop_zeros!(func)

julia> func
x[2]
3 Likes

Hello, I started using the Gurobi with JuMP on Julia recently. I am receiving numerical errors when running my code (Numerical trouble encountered). After doing some research I realized that my problem comes from the large range for the constraint matrices. I wanted to set some of the coefficients to zero. I found this page, however, this code is not working for me. Here is the code that I’m running and the error I’m getting:

code:

 using JuMP
 model = Model()

 @variable(model, x[1:2])

 A = rand(2, 2)
 b = rand(2)

 func = sum((A * x + b).^2)
 map_coefficients_inplace!(a -> round(a, digits=2), func)

 @objective(model, Min, func)
 print(model)

error:

UndefVarError: map_coefficients_inplace! not defined
Stacktrace:
 [1] top-level scope at In[4]:10

I would really appreciate it if you help me realize the problem.

This works for me

julia> using JuMP

julia> model = Model()
A JuMP Model
Feasibility problem with:
Variables: 0
Model mode: AUTOMATIC
CachingOptimizer state: NO_OPTIMIZER
Solver name: No optimizer attached.

julia> @variable(model, x[1:2])
2-element Array{VariableRef,1}:
 x[1]
 x[2]

julia> A = rand(2, 2)
2×2 Array{Float64,2}:
 0.233939  0.587798
 0.559358  0.572598

julia> b = rand(2)
2-element Array{Float64,1}:
 0.11297691388141651
 0.298978646383552  

julia> func = sum((A * x + b).^2)
0.3676088978662473 x[1]² + 0.9155925425691085 x[2]*x[1] + 0.6733753397704672 x[2]² + 0.38733164236038065 x[1] + 0.4752043958662899 x[2] + 0.10215201406351002

julia> map_coefficients_inplace!(a -> round(a, digits=2), func)
0.37 x[1]² + 0.92 x[2]*x[1] + 0.67 x[2]² + 0.39 x[1] + 0.48 x[2] + 0.1

julia> @objective(model, Min, func)
0.37 x[1]² + 0.92 x[2]*x[1] + 0.67 x[2]² + 0.39 x[1] + 0.48 x[2] + 0.1

julia> print(model)
Min 0.37 x[1]² + 0.92 x[2]*x[1] + 0.67 x[2]² + 0.39 x[1] + 0.48 x[2] + 0.1
Subject to

(jump) pkg> st
    Status `/private/tmp/jump/Project.toml`
  [4076af6c] JuMP v0.21.2

Please make sure you are on a recent version of JuMP.

1 Like

Interesting. It does not work for me. I couldn’t understand what did you mean by

(jump) pkg> st
    Status `/private/tmp/jump/Project.toml`
  [4076af6c] JuMP v0.21.2

I used the following code to check the version of my JuMP:

using Pkg
Pkg.status()

and I get

[4076af6c] JuMP v0.18.6

Then I tried to upgrade the version using

Pkg.update()

And I checked the version and it was still the same v0.18.6. I also tried upgrading with using Pkg Pkg.develop("JuMP") but still no luck. Here is the error:

Path `C:\Users\myaccount\.julia\dev\JuMP` exists and looks like the correct package. Using existing path.
  Resolving package versions...
Unsatisfiable requirements detected for package JuMP [4076af6c]:
 JuMP [4076af6c] log:
 ├─possible versions are: 0.21.2 or uninstalled
 ├─JuMP [4076af6c] is fixed to version 0.21.2
 └─found to have no compatible versions left with JuMPChance [bbd82366] 
   └─JuMPChance [bbd82366] log:
     ├─possible versions are: 0.5.0 or uninstalled
     └─restricted to versions * by an explicit requirement, leaving only versions 0.5.0

After all this, I checked the directory on my computer C:\Users\myaccount\.julia\packages\JuMP and there are two folders inside. From the Project.toml file inside the folders, one contains JuMP v0.18.6 and the other contains JuMP version = “0.21.2”. But from the julia I can only access the JuMP v0.18.6 every time I check, even when I delete the older version.

Also, I don’t know it has anything to do with this issue, but I used ATOM to install initial packages like (IJulia and Juno ) to use Julia with Jupyter Notebook. Sorry if I sound confusing, it is because I am confused at this point.

Here are the docs for the package manager:
https://docs.julialang.org/en/v1/stdlib/Pkg/index.html

JuMPChance is not compatible with recent versions of JuMP. Remove it, then upgrade

import Pkg
Pkg.rm("JuMPChance")
Pkg.update()

If you need to use JuMPChance, then you cannot use the code above, and I don’t think there was a good way of doing it in JuMP 0.18.

1 Like

I see. Yes, I was using JuMPChance. and this solved the problem regarding the map_coefficients_inplace! .

However, it would have taken me much more time to find out this issue if ever without asking here. Appreciate your help.

Although it is possible to work without JuMPChance, I rather use it because it saves me a lot of modification in my code at this point.
How about if I detect the small coefficients manually. i.e., let’s say I have the following affine expression:

JuMP.GenericAffExpr{Float64,Variable}[-5.93e-5, 4.33 ,3.12e-6 x, 2x ]

and I want to change the first and the third term to zero. Is there any way to do it?

You will have to poke around the internal fields of GenericAffExpr

and GenericQuadExpr

1 Like

Got it. Thanks.

Thanks to your help I was able to reduce the range of the QMatrix in my problem, but that didn’t fixed my numerical issue. I was wondering if you have any idea about this particular problem that I describe below:
The problem is that I have a large-scale model, and when I add a certain set of quadratic constraints to it, it gives me a numerical issue. I attached some of the summaries below.
With the Quadratic Constraint:

Model has 1343 quadratic constraints
Coefficient statistics:
  Matrix range     [4e-11, 4e+02]
  QMatrix range    [1e-08, 2e+02]
  Objective range  [1e+02, 3e+04]
  Bounds range     [3e-02, 1e+01]
  RHS range        [8e-19, 1e+01]
  QRHS range       [1e-03, 1e+02]
Warning: Model contains large matrix coefficient range
Warning: Quadratic constraints contain large coefficient range
….
Numerical trouble encountered

Without that specific quadratic constraint, I don’t have the numerical issue, see below:

Model has 1157 quadratic constraints
Coefficient statistics:
  Matrix range     [4e-11, 4e+02]
  QMatrix range    [1e+00, 1e+00]
  Objective range  [1e+02, 3e+04]
  Bounds range     [3e-02, 1e+01]
  RHS range        [8e-19, 1e+01]
  QRHS range       [7e-01, 9e+00]
Warning: Model contains large matrix coefficient range
….
Optimal 

Looking at the QMatrix range it is quite large, so I thought that is the source of the problem. I reduced the range of the QMatrix coefficients by removing some of the small ones (<10-3 or even less) but it didn’t solve the problem:

Model has 1343 quadratic constraints
Coefficient statistics:
  Matrix range     [4e-11, 4e+02]
  QMatrix range    [1e-03, 2e+02]
  Objective range  [1e+02, 3e+04]
  Bounds range     [3e-02, 1e+01]
  RHS range        [8e-19, 1e+01]
  QRHS range       [1e-03, 1e+02]
Warning: Model contains large matrix coefficient range
…..
Numerical trouble encountered

Therefore, the QMatrix range is not actually a problem (I even reduced it to smaller values but no luck). Since the model without the extra quadratic constraint is fine, then I suspect something else about this quadratic constraint is bothering the solver.

Any suggestions or ideas where the problem can be?

The issue is your linear constraints: Matrix range [4e-11, 4e+02]. Your coefficients range from 1e-11 to 1e2.

See https://www.gurobi.com/documentation/9.0/refman/num_grb_guidelines_for_num.html

Yes, however, without that specific quadratic constraint I have the same range on linear constraints, Matrix range [4e-11, 4e+02] and it was fine. That is where it bothers me. I realize that this range is a problem, however, my model is not created by hand, many parameters are calculated implicitly, which makes it hard to realize where 4e-11 come from…

it was fine.

There is no good rule for when you will encounter numerical difficulties.

You should consider changing the units of your problem. For example, instead of talking about 1e-6 meters, talk about 1 micron.

2 Likes