Try our new documentation site (beta).
Filter Content By
Version
Text Search
${sidebar_list_label} - Back
Filter by Language
diet_c.c
/* Copyright 2023, Gurobi Optimization, LLC */ /* Solve the classic diet model, showing how to add constraints to an existing model. */ #include <stdlib.h> #include <stdio.h> #include <math.h> #include "gurobi_c.h" int printSolution(GRBmodel* model, int nCategories, int nFoods); int main(int argc, char *argv[]) { GRBenv *env = NULL; GRBmodel *model = NULL; int error = 0; int i, j; int *cbeg, *cind, idx; double *cval, *rhs; char *sense; /* Nutrition guidelines, based on USDA Dietary Guidelines for Americans, 2005 http://www.health.gov/DietaryGuidelines/dga2005/ */ const int nCategories = 4; char *Categories[] = { "calories", "protein", "fat", "sodium" }; double minNutrition[] = { 1800, 91, 0, 0 }; double maxNutrition[] = { 2200, GRB_INFINITY, 65, 1779 }; /* Set of foods */ const int nFoods = 9; char* Foods[] = { "hamburger", "chicken", "hot dog", "fries", "macaroni", "pizza", "salad", "milk", "ice cream" }; double cost[] = { 2.49, 2.89, 1.50, 1.89, 2.09, 1.99, 2.49, 0.89, 1.59 }; /* Nutrition values for the foods */ double nutritionValues[][4] = { { 410, 24, 26, 730 }, { 420, 32, 10, 1190 }, { 560, 20, 32, 1800 }, { 380, 4, 19, 270 }, { 320, 12, 10, 930 }, { 320, 15, 12, 820 }, { 320, 31, 12, 1230 }, { 100, 8, 2.5, 125 }, { 330, 8, 10, 180 } }; /* Create environment */ error = GRBloadenv(&env, "diet.log"); if (error) goto QUIT; /* Create initial model */ error = GRBnewmodel(env, &model, "diet", nFoods + nCategories, NULL, NULL, NULL, NULL, NULL); if (error) goto QUIT; /* Initialize decision variables for the foods to buy */ for (j = 0; j < nFoods; ++j) { error = GRBsetdblattrelement(model, "Obj", j, cost[j]); if (error) goto QUIT; error = GRBsetstrattrelement(model, "VarName", j, Foods[j]); if (error) goto QUIT; } /* Initialize decision variables for the nutrition information, which we limit via bounds */ for (j = 0; j < nCategories; ++j) { error = GRBsetdblattrelement(model, "LB", j + nFoods, minNutrition[j]); if (error) goto QUIT; error = GRBsetdblattrelement(model, "UB", j + nFoods, maxNutrition[j]); if (error) goto QUIT; error = GRBsetstrattrelement(model, "VarName", j + nFoods, Categories[j]); if (error) goto QUIT; } /* The objective is to minimize the costs */ error = GRBsetintattr(model, "ModelSense", GRB_MINIMIZE); if (error) goto QUIT; /* Nutrition constraints */ cbeg = malloc(sizeof(int) * nCategories); if (!cbeg) goto QUIT; cind = malloc(sizeof(int) * nCategories * (nFoods + 1)); if (!cind) goto QUIT; cval = malloc(sizeof(double) * nCategories * (nFoods + 1)); if (!cval) goto QUIT; rhs = malloc(sizeof(double) * nCategories); if (!rhs) goto QUIT; sense = malloc(sizeof(char) * nCategories); if (!sense) goto QUIT; idx = 0; for (i = 0; i < nCategories; ++i) { cbeg[i] = idx; rhs[i] = 0.0; sense[i] = GRB_EQUAL; for (j = 0; j < nFoods; ++j) { cind[idx] = j; cval[idx++] = nutritionValues[j][i]; } cind[idx] = nFoods + i; cval[idx++] = -1.0; } error = GRBaddconstrs(model, nCategories, idx, cbeg, cind, cval, sense, rhs, Categories); if (error) goto QUIT; /* Solve */ error = GRBoptimize(model); if (error) goto QUIT; error = printSolution(model, nCategories, nFoods); if (error) goto QUIT; printf("\nAdding constraint: at most 6 servings of dairy\n"); cind[0] = 7; cval[0] = 1.0; cind[1] = 8; cval[1] = 1.0; error = GRBaddconstr(model, 2, cind, cval, GRB_LESS_EQUAL, 6.0, "limit_dairy"); if (error) goto QUIT; /* Solve */ error = GRBoptimize(model); if (error) goto QUIT; error = printSolution(model, nCategories, nFoods); if (error) goto QUIT; QUIT: /* Error reporting */ if (error) { printf("ERROR: %s\n", GRBgeterrormsg(env)); exit(1); } /* Free data */ free(cbeg); free(cind); free(cval); free(rhs); free(sense); /* Free model */ GRBfreemodel(model); /* Free environment */ GRBfreeenv(env); return 0; } int printSolution(GRBmodel* model, int nCategories, int nFoods) { int error, status, i, j; double obj, x; char* vname; error = GRBgetintattr(model, "Status", &status); if (error) return error; if (status == GRB_OPTIMAL) { error = GRBgetdblattr(model, "ObjVal", &obj); if (error) return error; printf("\nCost: %f\n\nBuy:\n", obj); for (j = 0; j < nFoods; ++j) { error = GRBgetdblattrelement(model, "X", j, &x); if (error) return error; if (x > 0.0001) { error = GRBgetstrattrelement(model, "VarName", j, &vname); if (error) return error; printf("%s %f\n", vname, x); } } printf("\nNutrition:\n"); for (i = 0; i < nCategories; ++i) { error = GRBgetdblattrelement(model, "X", i + nFoods, &x); if (error) return error; error = GRBgetstrattrelement(model, "VarName", i + nFoods, &vname); if (error) return error; printf("%s %f\n", vname, x); } } else { printf("No solution\n"); } return 0; }