Newer
Older
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
package ac.ed.lurg.country.gams;
import java.io.File;
import java.util.Map;
import ac.ed.lurg.ModelConfig;
import ac.ed.lurg.types.Item;
import ac.ed.lurg.types.LandCoverType;
import ac.ed.lurg.utils.LogWriter;
import com.gams.api.GAMSDatabase;
import com.gams.api.GAMSGlobals;
import com.gams.api.GAMSJob;
import com.gams.api.GAMSOptions;
import com.gams.api.GAMSParameter;
import com.gams.api.GAMSVariable;
import com.gams.api.GAMSVariableRecord;
import com.gams.api.GAMSWorkspace;
import com.gams.api.GAMSWorkspaceInfo;
public class GamsLandUseOptimiser {
private GamsLandUseData inputData;
public GamsLandUseOptimiser(GamsLandUseData inputData) {
this.inputData = inputData;
}
public void run() {
File workingDirectory = new File(ModelConfig.TEMP_DIR, "GamsTest");
workingDirectory.mkdir();
GAMSWorkspaceInfo wsInfo = new GAMSWorkspaceInfo();
wsInfo.setWorkingDirectory(workingDirectory.getAbsolutePath());
// wsInfo.setDebugLevel(DebugLevel.VERBOSE);
GAMSWorkspace ws = new GAMSWorkspace(wsInfo);
GAMSDatabase db = ws.addDatabase();
GAMSParameter parm = db.addParameter("previous_area", 1, "the previous area for each land use");
addLandUseArea(parm, LandCoverType.ARABLE);
addLandUseArea(parm, LandCoverType.PASTURE);
LogWriter.println("\nDemand");
parm = db.addParameter("demand", 1, "demand for crop");
addItemMapParm(parm, inputData.getProjectedDemand());
LogWriter.println("\nYield");
parm = db.addParameter("yield_ref", 1, "ref yield t per ha");
addItemMapParm(parm, inputData.getRefYield());
LogWriter.println("\nWorld input energy");
parm = db.addParameter("world_input_energy", 1, "average input energy from world exports used to determine if we should import or export energy per t");
addItemMapParm(parm, inputData.getWorldInputEnergy());
LogWriter.println("\nMax Export");
parm = db.addParameter("maxExport", 1, "max export for each crop based on world market");
addItemMapParm(parm, inputData.getMaxExport());
addScalar(db.addParameter("meatEfficency", 0, "efficency of converting feed and pasture into animal products"), inputData.getMeatEfficiency());
addScalar(db.addParameter("maxLandUseChange", 0, "max rate of land use change"), inputData.getMaxLandUseChange());
addScalar(db.addParameter("maxIntensity", 0, "max intensity which will rise over time"), inputData.getMaxIntensity());
addScalar(db.addParameter("tradeBarrier", 0, "trade barrier which adjust energy cost of imports"), inputData.getTradeBarrier());
addScalar(db.addParameter("landChangeEnergy", 0, "energy required to add ha of agricultural land"), inputData.getLandChangeEnergy());
addScalar(db.addParameter("minFeedRate", 0, "minimum rate of feed for producing animal products"), inputData.getMinFeedRate());
GAMSJob gamsJob = ws.addJobFromFile(ModelConfig.GAMS_MODEL);
GAMSOptions opt = ws.addOptions();
opt.defines("gdxincname", db.getName());
gamsJob.run(opt, db);
System.out.println(
"Modelstatus: " + GAMSGlobals.ModelStat.lookup( (int) gamsJob.OutDB().getParameter("ms").findRecord().getValue() ) +
", Solvestatus: " + GAMSGlobals.SolveStat.lookup((int) gamsJob.OutDB().getParameter("ss").findRecord().getValue()) );
GAMSVariable varAreas = gamsJob.OutDB().getVariable("area");
GAMSVariable varIntensities = gamsJob.OutDB().getVariable("intensity");
GAMSVariable varFeedAmount = gamsJob.OutDB().getVariable("feedAmount");
GAMSVariable varExports = gamsJob.OutDB().getVariable("exportAmount");
GAMSVariable varImports = gamsJob.OutDB().getVariable("importAmount");
double totalArea = 0;
for (GAMSVariableRecord rec : varAreas) {
LogWriter.println(String.format("%15s:\tarea= %.1f,\tintensity= %.3f,\tfeedAmount= %.0f,\texports= %.0f,\timports= %.0f",
rec.getKeys()[0], rec.getLevel(),
varIntensities.findRecord(rec.getKeys()[0]).getLevel(),
varFeedAmount.findRecord(rec.getKeys()[0]).getLevel(),
varExports.findRecord(rec.getKeys()[0]).getLevel(),
varImports.findRecord(rec.getKeys()[0]).getLevel()
));
totalArea += rec.getLevel();
// + " marginal=" + rec.getMarginal());
}
LogWriter.println(String.format(" Total area= %.1f", totalArea));
//cleanup(ws.workingDirectory());
}
private void addLandUseArea(GAMSParameter parm, LandCoverType landCover) {
double val = inputData.getLandCoverArea(landCover);
LogWriter.println(" " + landCover.getId() + ",\t\t" + val);
parm.addRecord(landCover.getId()).setValue(val);
}
private void addScalar(GAMSParameter param, double val) {
param.addRecord().setValue(val);
}
private void addItemMapParm(GAMSParameter parm, Map<Item, Double> itemMap) {
for (Map.Entry<Item, Double> entry : itemMap.entrySet()) {
LogWriter.println(" " + entry.getKey().getGamsName() + ",\t\t" + entry.getValue());
parm.addRecord(entry.getKey().getGamsName()).setValue(entry.getValue());
}
}
@SuppressWarnings("unused")
private void cleanup(String directory) {
File directoryToDelete = new File(directory);
String files[] = directoryToDelete.list();
for (String file : files) {
File fileToDelete = new File(directoryToDelete, file);
try {
fileToDelete.delete();
} catch(Exception e){
e.printStackTrace();
}
}
try {
directoryToDelete.delete();
} catch(Exception e) {
e.printStackTrace();
}
}
}