日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > c/c++ >内容正文

c/c++

【GAMS与C++的交互】

發(fā)布時間:2024/3/26 c/c++ 29 豆豆
生活随笔 收集整理的這篇文章主要介紹了 【GAMS与C++的交互】 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

GAMS與C++的交互(版本要求:GAMS25.1最多支持VS2017,GAMS38可以支持VS2019)

若有侵權或者不恰當?shù)氖褂?#xff0c;請及時聯(lián)系作者
若起到了作用請一鍵三聯(lián)
參考源代碼(官方代碼):
Tutorial (gams.com)

我的理解是,想要在C++里面運行GAMS程序,只需要把GAMS里面的數(shù)據(jù)和模型分別輸入到函數(shù)中進行運行即可

  • C++輸出到.gdx

    • 第一種方案:按照不同的分類格式一步一步地進行輸出,這是官方的例程,使用的是string
    #include "gams.h" #include <iostream> #include <fstream> #include <vector> #include <map> #include <cstdlib>using namespace gams; using namespace std;int main(int argc, char* argv[]) {cout << "---------- Transport GDX --------------" << endl;GAMSWorkspaceInfo wsInfo;if (argc > 1)wsInfo.setSystemDirectory(argv[1]);GAMSWorkspace ws(wsInfo);// define some data by using C++ data structuresvector<string> plants = {"Seattle", "San-Diego"};vector<string> markets = {"New-York", "Chicago", "Topeka"};map<string, double> capacity = {{ "Seattle", 350.0 }, { "San-Diego", 600.0 }};map<string, double> demand = {{ "New-York", 325.0 }, { "Chicago", 300.0 }, { "Topeka", 275.0 }};map<tuple<string, string>, double> distance = {{ make_tuple("Seattle", "New-York"), 2.5 },{ make_tuple("Seattle", "Chicago"), 1.7 },{ make_tuple("Seattle", "Topeka"), 1.8 },{ make_tuple("San-Diego", "New-York"), 2.5 },{ make_tuple("San-Diego", "Chicago"), 1.8 },{ make_tuple("San-Diego", "Topeka"), 1.4 }};// create new GAMSDatabase instanceGAMSDatabase db = ws.addDatabase();//C++----->gdx// 這是將string格式的打上標簽(添加成集合,集合名為canning plants)// add 1-dimensional set 'i' with explanatory text 'canning plants' to the GAMSDatabaseGAMSSet i = db.addSet("i", 1, "canning plants");for (string p : plants)i.addRecord(p);// add 1-dimensional set 'j' with explanatory text 'markets' to the GAMSDatabaseGAMSSet j = db.addSet("j", 1, "markets");for (string m : markets)j.addRecord(m);//添加一維parameter的方式(并且可以加上使用的是什么集合)// add parameter 'a' with domain 'i'GAMSParameter a = db.addParameter("a", "capacity of plant i in cases", i);for (string p : plants)a.addRecord(p).setValue(capacity[p]);//添加二維parameter的方式,之前也說過table是二維parameter的一種特殊形式// add parameter 'd' with domains 'i' and 'j'GAMSParameter d = db.addParameter("d", "distance in thousands of miles", i, j);for (auto t : distance)d.addRecord(get<0>(t.first), get<1>(t.first)).setValue(t.second);//添加scaler// add scalar 'f'GAMSParameter f = db.addParameter("f", "freight in dollars per case per thousand miles");f.addRecord().setValue(90);//輸出gdx文件,路徑我喜歡絕對路徑(這里的規(guī)則就是普通的C++的規(guī)則)// export the GAMSDatabase to a GDX file with name 'data.gdx' located in the 'workingDirectory' of the GAMSWorkspacedb.doExport("C:\\Users\\henry\\Desktop\\data.gdx");cout << "Content of GDX file 'data.gdx':";// add a new GAMSDatabase and initialize it from the GDX file just createdGAMSDatabase db2 = ws.addDatabaseFromGDX("C:\\Users\\henry\\Desktop\\data.gdx");//gdx------->c++//讀取我們先定義一個同格式的進行讀取// read data from symbols into C++ data structuresvector<string> iNew;for (GAMSSetRecord rec : db2.getSet("i"))iNew.push_back(rec.key(0));vector<string> jNew;for (GAMSSetRecord rec : db2.getSet("j"))jNew.push_back(rec.key(0));map<string, double> aNew;for (GAMSParameterRecord rec : db2.getParameter("a"))aNew[rec.key(0)] = rec.value();map<tuple<string, string>, double> dNew;for (GAMSParameterRecord rec : db2.getParameter("d"))dNew[make_tuple(rec.key(0), rec.key(1))] = rec.value();double fNew = db2.getParameter("f").firstRecord().value();cout << "i:" << endl;for (string s : iNew)cout << " " << s << endl;cout << "j:" << endl;for (string s : jNew)cout << " " << s << endl;cout << "a:" << endl;for (auto rec : aNew)cout << " " << rec.first << " : " << rec.second << endl;cout << "d:" << endl;for (auto rec : dNew)cout << " " << get<0>(rec.first) << ", " << get<1>(rec.first) << " : " << rec.second << endl;cout << "f:" << endl;cout << " " << fNew;return 0; }
    • 嘗試了一下使用數(shù)組設置set,發(fā)現(xiàn)并不可行,查了一下函數(shù)定義,發(fā)現(xiàn)成員為string,gams里面這個問題同樣存在
    GAMSSetRecord addRecord(); GAMSSetRecord addRecord(const std::string& key1); GAMSSetRecord addRecord(const std::string& key1, const std::string& key2); GAMSSetRecord addRecord(const std::string& key1, const std::string& key2, const std::string& key3);

    解決方案,直接強制類型轉換直接使用to_string()將int轉化成string,如果嫌麻煩的話,可以對函數(shù)進行重載,就在頭文件里復制一下加一行就可以了

    //寫的部分 //我來試試用數(shù)組的形式行不行,隨便定義一組數(shù)據(jù)double load[24] = { 0.0196,0.0186,0.0189,0.0202,0.0170,0.0767,0.0773,0.0889,0.2141,0.1255,0.0822,0.0558,0.340,0.0311,0.0266,0.0757,0.1181,0.1306,0.0639,0.0767,0.0735,0.0414,0.0286,0.0552 };// 先來定義一個集合setGAMSSet hour = db.addSet("hour", 1, "time scalar");for (int o = 1; o < 25; o++)hour.addRecord(to_string(o));GAMSParameter load_gams = db.addParameter("load", "load of system", hour);for (int o = 1; o < 25; o++)load_gams.addRecord(to_string(o)).setValue(load[o-1]); //讀的部分vector<string> read_hour;for (GAMSSetRecord rec : db2.getSet("hour"))read_hour.push_back(rec.key(0));map<string, double> load_new;for (GAMSParameterRecord rec : db2.getParameter("load"))load_new[rec.key(0)] = rec.value();
    • 第二種方案,使用string一口氣進行傳輸:使用GAMSJob這個類
  • 寫入.gdx文件

    // 輸入數(shù)據(jù)的格式 string getDataText() {return "Sets \n"" i canning plants / seattle, san-diego / \n"" j markets / new-york, chicago, topeka / ; \n""Parameters \n"" \n"" a(i) capacity of plant i in cases \n"" / seattle 350 \n"" san-diego 600 / \n"" \n"" b(j) demand at market j in cases \n"" / new-york 325 \n"" chicago 300 \n"" topeka 275 / ; \n"" \n""Table d(i,j) distance in thousands of miles \n"" new-york chicago topeka \n"" seattle 2.5 1.7 1.8 \n"" san-diego 2.5 1.8 1.4 ; \n"" \n""Scalar f freight in dollars per case per thousand miles /90/;\n"; } //如果需要用C++寫入GAMS的東西,直接將GAMS里面的內容用string按GAMS的格式寫出來輸入就可以GAMSJob t3 = ws.addJobFromString(getDataText());t3.run();//TODO: change doExport to export?t3.outDB().doExport("C:\\Users\\henry\\Desktop\\tdata.gdx");
  • 讀取我還沒搞明白,后續(xù)可能會更新

    (但是我覺得用不上,因為讀取完全可以通過gams讀取gdx文件在gams里面計算,沒必要使用C++調庫求解)

總結

以上是生活随笔為你收集整理的【GAMS与C++的交互】的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。