How to multiply vectors in Gurobi using Python?

Viewed 316

I am trying to write a linear constraint in Gurobi using Python API. Here in this picture in the first line.enter image description here As the picture can't be opened, the constraint is:

y_i≥(w_j a_i-γ_j )-M(1-x_ij ),i=1,…,m,j=1,…,k

import pandas as pd
import numpy as np 
import gurobipy as gp
from gurobipy import GRB

A=np.array([[ 7.6 , 8 ],
            [ 3  , 2.7],
            [ 0 , 0 ],
            [ 0.8 , 0.5],
            [ 6.6,  7.4],
            [ 6.7,  7.8],
            [ 1.9 , 2.6],
            [ 3.2 , 4.6],
            [ 6.4,  6.3],
            [10 , 10]])

m = A.shape[0]#number of rows in A
n = A.shape[1] #number of cols in A
M = 100000
k=2#cluster the data points into k clusters
# create model
model = gp.Model('hyperplane clustering')
# create variables
# Create a (m,k) array of binary variables
# x[i,j]=1 means that point ai is assigned to cluster j
x = model.addMVar((m,k), vtype=gp.GRB.BINARY,name="x")

y = model.addVars(m,lb=0.0, ub=gp.GRB.INFINITY, vtype=gp.GRB.CONTINUOUS, name="y")

w = {}
for i in range(k):
    for j in range(n):
        w[i,j] = model.addVar(lb=0.0, ub=1.0, vtype=gp.GRB.CONTINUOUS, name='w_%s_%s' %(i,j))
w = gp.tupledict(w)

gamma = model.addVars(k,vtype=gp.GRB.CONTINUOUS, name="gamma")

model.update()

for i in range(m):
    for j in range(k):
        wj = w.select(j,'*')
        wjmat = np.mat(wj).T        
        Amat = np.mat(A[i,:])
        model.addConstr(y[i] > (-np.dot(Amat,wjmat) +gamma[j])-M*(1-x[i,j]))

I am trying to write like this. But I always got the error' Incompatible vector dimensions' Hope someone can help me solve this. Thanks!

1 Answers

As already mentioned in the comments, you can't use numpy methods like np.dot with Gurobi objects. And since the third constraint can't be modelled directly with MVars and Gurobi's matrix interface, I'd recommend using Vars.

Then, simply write the dot product as a sum of products:

import gurobipy as gp
from gurobipy import quicksum as qsum

# A = ...

m, n = A.shape
k = 2
M = 100_000
model = gp.Model('hyperplane clustering')

# Variables
x = model.addVars(m, k, vtype="B", name="x")
y = model.addVars(m, vtype="C", name="y")
w = model.addVars(k, n, ub=1.0, vtype="C", name="w")
γ = model.addVars(k, vtype="C", name="γ")

for i in range(m):
    for j in range(k):
        wdota = qsum(w[j, r] * A[i, r] for r in range(n))
        # first constraint
        model.addConstr(y[i] >= wdota - γ[j] - M*(1-x[i,j]))
        # second constraint
        model.addConstr(y[i] >= -1.0*wdota + γ[j] - M*(1-x[i,j]))
Related