how to print a result in cplex other than the decision variable - variables

I want to print the value of pl[i]+pevdis[tvail][number]-pevch[tvail][number] as my result. The following is my code in Cplex.
int t=24;
int n=20;
int j=0;
range number =1..n;
range tavail=1..t;
float soc[number][tavail]=...;
//forcasted load at 0..4
float pl[tavail]=[10000000,7000000,9000000,6000000,12000000,6000000,4000000,15000000,9000000,12000000,6000000,8000000,10000000,7000000,9000000,6000000,12000000,6000000,4000000,15000000,9000000,12000000,6000000,8000000];
//soc of ev at 0..11
//generation
float pg[tavail]=[10000000,9500000,8500000,11000000,600000,7500000,10000000,9500000,8500000,11000000,600000,7500000,10000000,9500000,8500000,11000000,600000,7500000,10000000,9500000,8500000,11000000,600000,7500000];
//target load at 0..11
float pt[tavail]=[10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000,10000000];
//bus voltage at 0..11
float v[tavail]=[240,232,229,233,230,235,228,234,227,229,231,230,226,232,233,230,236,233,231,232,232,233,233,230];
//bus voltage at
// target bus voltage at 0..11
float vt[tavail]=[230,230,230,230,230,230,230,230,230,230,230,230,230,230,230,230,230,230,230,230,230,230,230,230];
//decision variable charging power ev
dvar float pevch[tavail][number] in 0..100000;
//decision variable discharging power of ev
dvar float pevdis[tavail][number] in 0..100000;
//levelised load
//objective function
minimize sum(i in tavail)((pt[i]-pl[i])+sum(j in number)-pevch[i][j]+sum(j in number)pevdis[i][j]);
subject to
{
forall(i in tavail,j in number)
if(pt[i]-pl[i]<0 && 0.7<soc[j][i]<0.9&& v[i]<vt[i])
pevdis[i][j]==soc[j][i]*100000;
else
pevdis[i][j]==0;
forall(i in tavail,j in number)
if(pt[i]-pl[i]>0 &&
soc[j][i]<=0.7 && v[i]>vt[i])
pevch[i][j]==soc[j][i]*100000;
else
pevch[i][j]==0;
}

After the subject to block you can do whatever printing you need.
For instance
minimize sum(i in tavail)((pt[i]-pl[i])+sum(j in number)-pevch[i][j]+sum(j in number)pevdis[i][j]);
subject to
{
forall(i in tavail,j in number)
if(pt[i]-pl[i]<0 && 0.7<soc[j][i]<0.9&& v[i]<vt[i])
pevdis[i][j]==soc[j][i]*100000;
else
pevdis[i][j]==0;
forall(i in tavail,j in number)
if(pt[i]-pl[i]>0 &&
soc[j][i]<=0.7 && v[i]>vt[i])
pevch[i][j]==soc[j][i]*100000;
else
pevch[i][j]==0;
}
int i=1;
int tvail=2;
int n2=3;
execute
{
writeln(
pl[i]+pevdis[tvail][n2]-pevch[tvail][n2] );
}

Related

Array issue with endbefore start in CPLEX

I am trying to add an Endbeforestartconstraint to my contrained programming problem. However, I receive an error saying that my end beforestart is not an array type. I do not understand this as I almost copied the constraint and data from the sched_seq example in CPLEX, I only changed it to integers.
What I try to accomplish with the constraint, is that task 3 and task 1 will be performed before task 2 will start.
How I can fix the array error for this constraint?
Please find below the relevant parts of my code
tuple Precedence {int pre;int post;};
{Precedence} Precedences = {<3,2>,<1,2>};
dvar interval task[j in Jobs] in release..due;
dvar interval opttask[j in Jobs][m in Machines] optional size duration[j][m];
dvar sequence tool[m in Machines] in all(j in Jobs) opttask[j][m]
dexpr int makespan = max(j in Jobs, m in Machines)(endOf(opttask[j][m]));
minimize makespan;
subject to {
// Each job needs one unary resource of the alternative set s (28)
forall(j in Jobs){
alternative(task[j], all(m in Machines) opttask[j][m]);
}
// No overlap on machines
forall(j in Jobs)
forall(p in Precedences)
endBeforeStart(opttask[j][p.pre],opttask[j][p.post]);
forall(m in Machines){
noOverlap(tool[m],transitionTimes);
}
};
execute {
writeln(task);
dat.
nbMachines = 2;
nbJobs = 3;
duration = [
[5,6],
[4,4],
[5,8]
];
release = 1;
due = 30;
There are several errors in your model, on ranges or on inverted indices.
Also, next time, please post a complete program showing the problem, not just a partial one, this may help you to get quicker answers.
A corrected program:
using CP;
int nbMachines = 2;
int nbJobs = 3;
range Machines = 0..nbMachines-1;
range Jobs = 0..nbJobs-1;
int duration[Jobs][Machines] = [
[5,6],
[4,4],
[5,8]
];
int release = 1;
int due = 30;
tuple Precedence {int pre;int post;};
{Precedence} Precedences = {<2,1>,<0,1>};
dvar interval task[j in Jobs] in release..due;
dvar interval opttask[j in Jobs][m in Machines] optional size duration[j][m];
dvar sequence tool[m in Machines] in all(j in Jobs) opttask[j][m];
dexpr int makespan = max(j in Jobs, m in Machines)(endOf(opttask[j][m]));
minimize makespan;
subject to {
// Each job needs one unary resource of the alternative set s (28)
forall(j in Jobs){
alternative(task[j], all(m in Machines) opttask[j][m]);
}
// No overlap on machines
forall(m in Machines)
forall(p in Precedences)
endBeforeStart(opttask[p.pre][m],opttask[p.post][m]);
};
execute {
writeln(task);
}
You must have values in p.pre or p.post that are outside of the array indexing range.

How to minimize total cost of external resource in MRCPSP?

Hi I'm trying to make a model with objective function to minimize cost of mode 2 usage( mode with using external resource). I confuse when I want to make a limitation total time <=21 the result is no value, but when I set the time <= 50 the result was came out, although the result when I running the model only spending time 25.
tuple Task {
key int id;
{int} succs;
int RelDate;
}
{Task} Tasks = ...;
tuple Mode {
key int taskId;
key int id;
int pt;
int costprod;
int dmdIntRes [IntRes];
int dmdExtRes [ExtRes];
int ExtCost;
}
{Mode} Modes = ...;
dvar interval Taskss [t in Tasks] in t.RelDate..(maxint div 2)-1;
dvar interval mode[m in Modes] optional size m.pt;
dexpr int totaltime = sum(m in Modes) presenceOf(mode[m]) * ( m.pt); //boolean expression
//dexpr int totalExtCost = sum(m in Modes) presenceOf(mode[m])* (m.ExtCost * m.pt);
cumulFunction IntResUsage[r in IntRes] =
sum (m in Modes: m.dmdIntRes[r]>0) pulse(mode[m], m.dmdIntRes[r]);
cumulFunction ExtResUsage[r in ExtRes] =
sum (m in Modes: m.dmdExtRes[r]>0) pulse(mode[m], m.dmdExtRes[r]);
execute {
cp.param.FailLimit = 10000;
}
minimize sum(m in Modes) (m.ExtCost * m.pt) * maxl (presenceOf(mode[m]));
//minimize max(t in Tasks) endOf(Taskss[t]);
subject to {
//Alternative mode of resource productivity in Cost's unit
forall (t in Tasks, m in Modes) {
// if(m.costprod *m.pt == 0 && 0 <= 559717712) presenceOf(mode[first(Modes)]);
alternative(Taskss[t], all(m in Modes: m.taskId==t.id) mode[m]);
}
forall (t in Tasks, m in Modes)
(sum(t in Tasks)sum(m in Modes) m.costprod * m.pt <= 285740966 in 0..NbDays-14) != presenceOf(mode[first(Modes)]);
//External resource's budget limitation
forall ( t in Tasks, m in Modes )
totaltime <= 50;
//forall ( m in Modes )
//totalExtCost <= 30000000;
//Resource Usage
forall (r in IntRes)
IntResUsage[r] <= CapIntRes[r];
forall (r in ExtRes)
ExtResUsage[r] <= CapExtRes[r];
Could you simplify your model so that it illustrates your problem ?
I do not see any value 50 or 25 in the model.
Also:
I do not see why you are using a “max” here:
minimize sum(m in Modes) (m.ExtCost * m.pt) * maxl (presenceOf(mode[m]));
I do not see why you post this constraint for each task and each mode (!). It is independent from the tasks and the modes: forall ( t in Tasks, m in Modes ) { totaltime <= 100; }
By the way, for readability reasons, you could also rewrite your expressions: “presenceOf(mode[m]) * ( m.pt)” as “sizeOf(mode[m])”. If the model duration is a constant, both formulations should be more or less similar from a performance perspective, but if the duration is a decision variable, the formulation with “sizeOf(model[m])” will definitively be better.
For the 'min', you should neither use the min or the max as your are dealing with a singleton, you directly use the presenceOf.
So I would simplify the formulation as follows:
dvar interval Tasks [t in Tasks] in t.RelDate..(maxint div 2)-1;
dvar interval mode[m in Modes] optional size m.pt;
dexpr int totaltime = sum(m in Modes) sizeOf(mode[m]);
dexpr int totalExtCost = sum(m in Modes) (m.ExtCost*sizeOf(mode[m]));
cumulFunction IntResUsage[r in IntRes] =
sum (m in Modes: m.dmdIntRes[r]>0) pulse(mode[m], m.dmdIntRes[r]);
cumulFunction ExtResUsage[r in ExtRes] =
sum (m in Modes: m.dmdExtRes[r]>0) pulse(mode[m], m.dmdExtRes[r]);
execute {
cp.param.FailLimit = 10000;
}
minimize totalExtCost;
subject to {
// Alternative mode of resource productivity in Cost's unit
forall (t in Tasks)
alternative(Tasks[t], all(m in Modes: m.taskId==t.id) mode[m]);
// I have no hint what the constraints below are supposed to do !
// forall (t in Tasks, m in Modes)
// (sum(t in Tasks) sum(m in Modes) m.costprod * m.pt <= 285740966 in 0..NbDays-14) != presenceOf(mode[first(Modes)]);
// External resource's budget limitation
totaltime <= 50;
// totalExtCost <= 30000000;
// Resource Usage
forall (r in IntRes)
IntResUsage[r] <= CapIntRes[r];
forall (r in ExtRes)
ExtResUsage[r] <= CapExtRes[r];
}
Then I still do not understand the problem with limiting the "totalTime" to 50. It does not prevent to compute a solution with "totalTime=25" indeed, as 25<=50.
In fact I do not understand your problem. You seem to say that the problem with "totalTime<=21" is infeasible, and that when you post a constraint "totalTime<=50" it finds a solution where "totalTime=25". I don't see where is the problem here ...

How to make a if and else in alternative function in OPL?

I want to make if the earn value is not same with the plan then choose alternative 2, if same then choose alternative 1. I used tuple mode to determine the 2 alternative in OPL using CP(constraint programming)
I still stuck until this part
**subject to {
forall (p in Precedences, m in Modes) {
alternative(Tasks[p], all(m in Modes: m.taskId==p.id) mode[m]);**
thanks, I need this part to finish my master thesis, because I don't have a basic about programming
You can use presenceOf.
using CP;
int v=1;
// if v is 1 we choose a1p[1] , if not a1p[2];
dvar interval a1;
dvar interval a1p[i in 1..2] optional size i;
subject to {
alternative(a1, a1p);
(v==1) == (presenceOf(a1p[1])==1);
};
execute
{
writeln(a1);
}
gives
<1 0 1 1>
but if I change v=1 to v=2 then I get
<1 0 2 2>
thanks for response my question, I felt bless. this code plicable to using tuple? because I make my mode at tuple? when I tried using range 1..2 the dvar was error. this is my original code
tuple Mode {
key int taskId;
key int id;
int pt;
int costprod;
int dmdIntRes [IntRes];
int dmdExtRes [ExtRes];
}
{Mode} Modes = ...;
dvar interval Tasks [p in Precedences]in p.RelDate..EndMax ; //in p.RelDate..EndMax in 0..EndMax
dvar interval mode[m in Modes] optional size m.pt;
cumulFunction IntResUsage[r in IntRes] =
sum (m in Modes: m.dmdIntRes[r]>0) pulse(mode[m], m.dmdIntRes[r]);
cumulFunction ExtResUsage[r in ExtRes] =
sum (m in Modes: m.dmdExtRes[r]>0) pulse(mode[m], m.dmdExtRes[r]);
execute {
cp.param.FailLimit = 10000;
}
minimize max(p in Precedences) endOf(Tasks[p]);
subject to {
forall (p in Precedences, m in Modes) {
alternative(Tasks[p], all(m in Modes: m.taskId==p.id) mode[m]);

How to compare float variables using strict inequality?

I'm trying to implement a maximize problem. In one part I am trying to compare a float to a dvar float for which I get the Error "The operator >(float, dvar float) is not available in the context of CPLEX." Using >= works, but I get wrong results. Is there any way to work around the error?
float price[D][A] = ...;
float volaforecast[D] = ...;
dvar float vola;
dvar int change[D][A];
maximize sum(d in D, a in A)(price[d][a] * change[d][a]);
subject to {
forall(d in D: d > 1) {
( volaforecast[d] <= vola &&
volaforecast[d-1] > vola &&
change[d]["a"] == 0
) || (
volaforecast[d] > vola &&
volaforecast[d-1] <= vola &&
change[d]["a"] == 1
);
}
}
As Tim mentioned in his comment, you should use var >= value + epsilon. Strict inequality doesn't fit the Linear Programming paradigm that CPLEX uses.

Create a Fraction array

I have to Create a dynamic array capable of holding 2*n Fractions.
If the dynamic array cannot be allocated, prints a message and calls exit(1).
It next fills the array with reduced random Fractions whose numerator
is between 1 and 20, inclusive; and whose initial denominator
is between 2 and 20, inclusive.
I ready did the function that is going to create the fraction and reduced it. this is what I got. When I compiled and run this program it crashes I cant find out why. If I put 1 instead of 10 in the test.c It doesn't crash but it gives me a crazy fraction. If I put 7,8,or 11 in the test.c it will crash. I would appreciate if someone can help me.
FractionSumTester.c
Fraction randomFraction(int minNum, int minDenom, int max)
{
Fraction l;
Fraction m;
Fraction f;
l.numerator = randomInt(minNum, max);
l.denominator = randomInt(minDenom, max);
m = reduceFraction(l);
while (m.denominator <= 1)
{
l.numerator = randomInt(minNum, max);
l.denominator = randomInt(minDenom, max);
m = reduceFraction(l);
}
return m;
}
Fraction *createFractionArray(int n)
{
Fraction *p;
int i;
p = malloc(n * sizeof(Fraction));
if (p == NULL)
{
printf("error");
exit(1);
}
for(i=0; i < 2*n ; i++)
{
p[i] = randomFraction(1,2,20);
printf("%d/%d\n", p[i].numerator, p[i].denominator);
}
return p;
}
this is the what I am using to test this two functions.
test.c
#include "Fraction.h"
#include "FractionSumTester.h"
#include <stdio.h>
int main()
{
createFractionArray(10);
return 0;
}
In your createFractionArray() function, you malloc() space for n items. Then, in the for loop, you write 2*n items into that space... which overruns your buffer and causes the crash.