Element uit Array verwijderen

Status
Niet open voor verdere reacties.
@Cow18,
Heb zo is de 84 getallen kleiner gemaakt door deling met 1000 of met aftrek van 1500.
Ging met je code vooruit als een snel-treintje...
Daarna x 1000 of + 1500 maar kreeg resultaten met kleine afwijking.
Hoe jij dat kon met 100 getallen is ook niet te vatten, hoor!
De magie bij Java zit hem volgens mij in JSON(JavaScript Object Notation).
Vertalen naar VBA is (denk ik) niet direct mogelijk maar wil eens uitzoeken hoe je volledige pagina in Javascript kan gebruiken
met VBA. Het zal zeker deuren openen in Excel... Voor functies uit Javascript gebruik ik de Microsoft Script Control 1.0
Die ondersteunt geen 64BIT maar daar is omweg voor.

@Snb,
Die Java kan je vinden in mijn post #31 (zonder Underscore).
Ben aan het uitzoeken welke code gebruikt wordt uit Underscore en zal later alles plaatsen.

Groetjes allebei,
Leika
 
Laatst bewerkt door een moderator:
dat was eigenlijk een leuk tip, trek van alle getallen 1500 af, dus doe ik het iets extremer, ik trek er 3500 van af, net iets minder dan het kleinste getal (3502).

Dan laat ik de macro lopen.
Grappig na 13 sec bereik een resultaat die in de buurt van Java komt. (som van de absolute afwijkingen = 6 à 7)
Daarna ga ik nog 37 sec door om dat resultaat nog te halveren (som van de absolute afwijkingen = 3.43)

Bij Java zitten de sommen van de getallen tss 5357-5360.
Bij Solver zitten die sommen tss 5357-5358.

Straks moet er wel weer die 3500 bijgeteld worden om met de oorspronkelijke cijfers te kunnen werken.

Conclusie : Java is een factor 10 sneller om met een even goed resultaat te komen.
Solver gaat dan nog even de puntjes op de i zetten en bereikt een resultaat die niet meer te verbeteren valt.
Zonder die aftrek van die 3500 werkte dit niet.
Wat zijn we weer aan het mieren******! (blijkbaar zit er een autocensuur op deze site, en wordt "n e u k e n" vervangen door sterretjes)
 

Bijlagen

  • Forum 12maal7(3).xls
    149,5 KB · Weergaven: 24
Laatst bewerkt:
Dag Cow18,

Je hebt de vijand of vriend(?) verslagen, hehe

In die Java code gebruiken ze random met de Simulated annealing
De code is nu alles in één html pagina en heb overal console output opgenomen zodat je eventueel kan zien hoe ze te werk gaan.

Groetjes,
Leika

Code:
<!doctype html>
<html lang="en">
    <head>
        <meta charset="utf-8">
        <meta http-equiv="X-UA-Compatible" content="IE=edge">
        <meta name="viewport" content="width=device-width, initial-scale=1">
        <title>Pack builder</title>
        <!--<link rel="stylesheet" href="***.css">-->

        <style>
            body {
                padding-top: 60px;
                margin-left: 10px;
            }
            button {
                margin-top: 10px;
                margin-right: 0px;
                margin-bottom: 10px;
                margin-left: 0px;
                padding-top: 5px;
                padding-right: 10px;
                padding-bottom: 5px;
                padding-left: 10px;
            }
            textarea {
                margin-top: 10px;
                margin-right: 0px;
                margin-bottom: 10px;
                margin-left: 0px;
                padding-top: 5px;
                padding-right: 10px;
                padding-bottom: 5px;
                padding-left: 10px;
            }
        </style>
    </head>
    <body>
        Cells Per Pack (id = cellsPerPack) :
        <input type="text" id="cellsPerPack" value="12">
        
        <br/>
        <br/>
        Cells (separated by space) (id = cells) : <br/>
        <textarea style="width:300px;height:200px;" type="text" id="cells">3602, 3990, 3615, 4227, 3940, 4195, 3700, 3569, 4012, 3948, 4236, 4200, 4249, 4239, 4300, 3595, 4008, 3719, 4007, 3612, 3711, 4010, 3740, 4189, 4199, 4008, 4161, 3685, 4233, 3633, 4265, 3659, 4151, 3584, 3581, 4295, 3635, 3615, 3720, 4168, 3646, 3581, 4175, 3555, 4258, 4248, 3962, 4280, 4274, 4282, 3738, 3631, 3617, 4265, 3688, 4208, 3595, 4179, 4298, 4230, 4156, 4288, 4275, 4239, 4253, 3943, 3667, 3639, 3625, 4157, 3642, 4298, 4228, 3940, 3760, 3552, 4228, 3703, 4297, 3719, 3703, 3619, 3643, 4013
        </textarea>
        <br/>
        <button id="optimizeBtn">Optimize</button>
        <br/>
        Optimized Pack (id = optimizedCells) <br/>
        <textarea style="width:500px;height:510px;" type="text" id="optimizedCells"></textarea>
        
        <script >
            /*
            The MIT License (MIT)
            Copyright (c) 2016 Dex Wood

            Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:

            The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.

            THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
            */
            var optimizeBtn = document.getElementById("optimizeBtn");
            var cellsPerPackInput = document.getElementById('cellsPerPack');
            var cellsInput = document.getElementById("cells");

            optimizeBtn.onclick = function () {
                var cellsPerPack = parseInt(cellsPerPackInput.value);                                   //console.log("*** cellsPerPack " + cellsPerPack);
                var cells = _.map(cellsInput.value.split(","), function (c) {return parseInt(c);});     //console.log("*** cells " + cells); // split string by comma
                var numPacks = cells.length / cellsPerPack;                                             //console.log("*** numPacks " + numPacks);
                var averageDiv = parseInt(sum(cells) / numPacks);                                       //console.log("*** averageDiv " + averageDiv);
                var solution = simulatedAnnealingBatteries(cells, cellsPerPack, averageDiv);            //console.log("*** solution " + solution);
                var optimizedCellsInput = document.getElementById("optimizedCells");
                var solutionPacks = multiPartition(solution, cellsPerPack);
                var solutionOutput = "";                                                                //console.log("*** Cost: " + cost(solution, numPacks, averageDiv));
                solutionOutput += "Optimized Packs\n";                                                  // a += b -> a = a + b 
                solutionOutput += "---------------\n\n";
                solutionOutput += "Pack average: " + parseInt(averageDiv) + "\n\n";
                for (var idx in solutionPacks) {
                    var packNum = parseInt(idx) + 1;
                    solutionOutput += "Pack " + packNum + "\n";
                    solutionOutput += JSON.stringify(_.sortBy(solutionPacks[idx], function (d) 
                    {return -d;
                    })) + "\n";        console.log("*** OutPut1 " + solutionOutput);                     //console.log("*** Sum " + sum(solutionPacks[idx]));
                    solutionOutput += "Verschil : " + parseInt(sum(solutionPacks[idx]) - averageDiv) + "\n\n";
                }
                optimizedCellsInput.value = solutionOutput;                                             //console.log("*** OutPut " + solutionOutput);
            }
            // -----------------------------------------
            // FUNCTIES 
            // -----------------------------------------
            function multiPartition(cells, n) {
                var partitions = [];
                var packs = (cells.length / n);
                for (var i = 0; i < packs; i++) {
                    partitions.push([]);
                }
                for (var idx in cells) {
                    partitions[idx % packs].push(cells[idx]);
                }
                return _.filter(partitions, function (p) {
                    return p.length > 0;
                })
            }

            function cost(solution, numPacks, averageDiv) {
                var packDivision = multiPartition(solution.slice(), numPacks);
                var totalCost = _.map(packDivision, function (p) {
                    return Math.abs(sum(p) - averageDiv);
                });
                return sum(totalCost);
            }

            function acceptanceProb(curCost, cost, temperature) {
                return Math.pow(Math.E, (curCost - cost) / temperature);
            }

            function sum(items) {
                return _.reduce(items, function (a, b) {
                    return a + b;
                });
            }
            
            /*  Simulated annealing ->   https://nl.wikipedia.org/wiki/Simulated_annealing
                JavaScript Assignment Operators
                Operator     Example	     Same As
                ---------------------------------------
                    =	     x = y           x = y
                    +=	     x += y	         x = x + y
                    -=	     x -= y	         x = x - y
                    *=	     x *= y	         x = x * y
                    /=	     x /= y	         x = x / y
                    %=	     x %= y	         x = x % y
                    
                Number.MAX_VALUE    the largest possible number in JavaScript and VBA       1.7976931348623157e+308 
                Math.random()       returns a random number between 0 and 1                 0.7290565902133195
                slice()             The slice() method returns the selected elements in an array, as a new array object
                split()             The split() method is used to split a string into an array of substrings, and returns the new array. Does not change the original string
                _.sortBy            The _.sortBy() function is used to sort all the elements of the list in ascending order according to the function given to it as a parameter.
                
            */
            function simulatedAnnealingBatteries(cells, numPacks, avgDiv) {
                var currentSolution = cells.slice();                                //console.log("*** currentSolution " + currentSolution);  // 
                var curCost = Number.MAX_VALUE;                                     //console.log("*** curCost " + curCost);                  // 
                var minTemperature = 1e-6;                                          //console.log("*** minTemperature " + minTemperature);    // 0.000001
                var temperature = 1.0;                                              //console.log("*** temperature " + temperature);          // 1
                var cooling = 0.93;                                                 //console.log("*** cooling " + cooling);                  // 0.93
                while (temperature > minTemperature) {
                    for (var i = 0; i < 100; i++) {                                 // loop through a block of code 100 times
                        var neighboringSolution = currentSolution.slice();          //console.log("*** ("+ i +") neighboringSolution " + neighboringSolution);
                        var first = parseInt(Math.random() * cells.length);         //console.log("*** ("+ i +") first " + first);            // 
                        var second = parseInt(Math.random() * cells.length);        //console.log("*** ("+ i +") second " + second);
                        var tmp = neighboringSolution[first];                       //console.log("*** ("+ i +") tmp " + tmp);
                        
                        neighboringSolution[first] = neighboringSolution[second];   //console.log("*** ("+ i +") neighboringSolution[first] " + neighboringSolution[first]);
                        neighboringSolution[second] = tmp;                          //console.log("*** ("+ i +") neighboringSolution[second] " + neighboringSolution[second]);
                        var newCost = cost(neighboringSolution, numPacks, avgDiv);  //console.log("*** ("+ i +") newCost " + newCost);
                        var prob = acceptanceProb(curCost, newCost, temperature);   //console.log("*** ("+ i +") prob " + prob);
                        
                        if (prob > Math.random()) {
                            currentSolution = neighboringSolution;
                            curCost = newCost;
                        }
                    }
                    temperature *= cooling;                                         //console.log("*** |||||| *** ("+ i +") temperature " + temperature);  // x = x * y
                }
                                                                                    //console.log("*** loop i = " + i);
                return currentSolution;
            }
            //-------------------------------------------------------------------------------------
            //  Underscore.js 1.9.1
            //  http://underscorejs.org
            //  (c) 2009-2018 Jeremy Ashkenas, DocumentCloud and Investigative Reporters & Editors
            //  Underscore may be freely distributed under the MIT license.
            //-------------------------------------------------------------------------------------
            (function() {
                  // Baseline setup
                  // --------------
                  // Establish the root object, `window` (`self`) in the browser, `global`
                  // on the server, or `this` in some virtual machines. We use `self`
                  // instead of `window` for `WebWorker` support.
                  var root = typeof self == 'object' && self.self === self && self ||
                            typeof global == 'object' && global.global === global && global ||
                            this ||
                            {};

                  // Save the previous value of the `_` variable.
                  var previousUnderscore = root._;

                  // All **ECMAScript 5** native function implementations that we hope to use
                  // are declared here.
                  var nativeIsArray = Array.isArray,
                      nativeKeys = Object.keys,
                      nativeCreate = Object.create;

                  // Naked function reference for surrogate-prototype-swapping.
                  var Ctor = function(){};

                  // Create a safe reference to the Underscore object for use below.
                  var _ = function(obj) {
                    if (obj instanceof _) return obj;
                    if (!(this instanceof _)) return new _(obj);
                    this._wrapped = obj;
                  };

                  // Export the Underscore object for **Node.js**, with
                  // backwards-compatibility for their old module API. If we're in
                  // the browser, add `_` as a global object.
                  // (`nodeType` is checked to ensure that `module`
                  // and `exports` are not HTML elements.)
                  if (typeof exports != 'undefined' && !exports.nodeType) {
                        if (typeof module != 'undefined' && !module.nodeType && module.exports) {
                          exports = module.exports = _;
                        }
                        exports._ = _;
                  } else {
                        root._ = _;
                  }

                  // Internal function that returns an efficient (for current engines) version
                  // of the passed-in callback, to be repeatedly applied in other Underscore
                  // functions.
                  var optimizeCb = function(func, context, argCount) {
                        if (context === void 0) return func;
                        switch (argCount == null ? 3 : argCount) {
                              case 1: return function(value) {
                                return func.call(context, value);
                              };
                              // The 2-argument case is omitted because we’re not using it.
                              case 3: return function(value, index, collection) {
                                return func.call(context, value, index, collection);
                              };
                              case 4: return function(accumulator, value, index, collection) {
                                return func.call(context, accumulator, value, index, collection);
                              };
                        }
                        return function() {
                              return func.apply(context, arguments);
                        };
                  };

                  var builtinIteratee;

                  // An internal function to generate callbacks that can be applied to each
                  // element in a collection, returning the desired result — either `identity`,
                  // an arbitrary callback, a property matcher, or a property accessor.
                  var cb = function(value, context, argCount) {
                        if (_.iteratee !== builtinIteratee) return _.iteratee(value, context);
                        if (value == null) return _.identity;
                        if (_.isFunction(value)) return optimizeCb(value, context, argCount);
                        if (_.isObject(value) && !_.isArray(value)) return _.matcher(value);
                        return _.property(value);
                  };

                  var shallowProperty = function(key) {
                        return function(obj) {
                          return obj == null ? void 0 : obj[key];
                        };
                  };

                  // Helper for collection methods to determine whether a collection
                  // should be iterated as an array or as an object.
                  // Related: http://people.mozilla.org/~jorendorff/es6-draft.html#sec-tolength
                  // Avoids a very nasty iOS 8 JIT bug on ARM-64. #2094
                  var MAX_ARRAY_INDEX = Math.pow(2, 53) - 1;
                  var getLength = shallowProperty('length');
                  var isArrayLike = function(collection) {
                        var length = getLength(collection);
                        return typeof length == 'number' && length >= 0 && length <= MAX_ARRAY_INDEX;
                  };

                  // Collection Functions
                  // --------------------

                  // The cornerstone, an `each` implementation, aka `forEach`.
                  // Handles raw objects in addition to array-likes. Treats all
                  // sparse array-likes as if they were dense.
                  _.each = _.forEach = function(obj, iteratee, context) {
                        iteratee = optimizeCb(iteratee, context);
                        var i, length;
                        if (isArrayLike(obj)) {
                          for (i = 0, length = obj.length; i < length; i++) {
                            iteratee(obj[i], i, obj);
                          }
                        } else {
                          var keys = _.keys(obj);
                          for (i = 0, length = keys.length; i < length; i++) {
                            iteratee(obj[keys[i]], keys[i], obj);
                          }
                        }
                        return obj;
                  };

                  // Return the results of applying the iteratee to each element.
                  _.map = _.collect = function(obj, iteratee, context) {
                        iteratee = cb(iteratee, context);
                        var keys = !isArrayLike(obj) && _.keys(obj),
                            length = (keys || obj).length,
                            results = Array(length);
                        for (var index = 0; index < length; index++) {
                          var currentKey = keys ? keys[index] : index;
                          results[index] = iteratee(obj[currentKey], currentKey, obj);
                        }
                        return results;
                  };


                  // Create a reducing function iterating left or right.
                  var createReduce = function(dir) {
                        // Wrap code that reassigns argument variables in a separate function than
                        // the one that accesses `arguments.length` to avoid a perf hit. (#1991)
                        var reducer = function(obj, iteratee, memo, initial) {
                          var keys = !isArrayLike(obj) && _.keys(obj),
                              length = (keys || obj).length,
                              index = dir > 0 ? 0 : length - 1;
                          if (!initial) {
                                memo = obj[keys ? keys[index] : index];
                                index += dir;
                          }
                          for (; index >= 0 && index < length; index += dir) {
                                var currentKey = keys ? keys[index] : index;
                                memo = iteratee(memo, obj[currentKey], currentKey, obj);
                          }
                          return memo;
                        };

                        return function(obj, iteratee, memo, context) {
                              var initial = arguments.length >= 3;
                              return reducer(obj, optimizeCb(iteratee, context, 4), memo, initial);
                        };
                  };

                  // **Reduce** builds up a single result from a list of values, aka `inject`,
                  // or `foldl`.
                  _.reduce = _.foldl = _.inject = createReduce(1);

                  // Return all the elements that pass a ****h test.
                  // Aliased as `select`.
                  _.filter = _.select = function(obj, predicate, context) {
                        var results = [];
                        predicate = cb(predicate, context);
                        _.each(obj, function(value, index, list) {
                          if (predicate(value, index, list)) results.push(value);
                        });
                        return results;
                  };

                  // Convenience version of a common use case of `map`: fetching a property.
                  _.pluck = function(obj, key) {
                        return _.map(obj, _.property(key));
                  };

                  // Sort the object's values by a criterion produced by an iteratee.
                  _.sortBy = function(obj, iteratee, context) {
                        var index = 0;
                        iteratee = cb(iteratee, context);
                        return _.pluck(_.map(obj, function(value, key, list) {
                          return {
                            value: value,
                            index: index++,
                            criteria: iteratee(value, key, list)
                          };
                        }).sort(function(left, right) {
                          var a = left.criteria;
                          var b = right.criteria;
                          if (a !== b) {
                            if (a > b || a === void 0) return 1;
                            if (a < b || b === void 0) return -1;
                          }
                          return left.index - right.index;
                        }), 'value');
                  };

                    // Is a given value an array?
                  // Delegates to ECMA5's native Array.isArray
                  _.isArray = nativeIsArray || function(obj) {
                        return toString.call(obj) === '[object Array]';
                  };


                  // Add some isType methods: isArguments, isFunction, isString, isNumber, isDate, isRegExp, isError, isMap, isWeakMap, isSet, isWeakSet.
                  _.each(['Arguments', 'Function', 'String', 'Number', 'Date', 'RegExp', 'Error', 'Symbol', 'Map', 'WeakMap', 'Set', 'WeakSet'], function(name) {
                        _['is' + name] = function(obj) {
                          return toString.call(obj) === '[object ' + name + ']';
                        };
                  });

                    // Utility Functions
                    // -----------------

                  // Creates a function that, when passed an object, will traverse that object’s
                  // properties down the given `path`, specified as an array of keys or indexes.
                  _.property = function(path) {
                        if (!_.isArray(path)) {
                          return shallowProperty(path);
                        }
                        return function(obj) {
                          return deepGet(obj, path);
                        };
                  };

            }());
        </script>
    </body>
</html>
 
ik had het werkblad al eens herschikt, want het was een rommeltje.
Links je 84 getallen en wat cijfertjes
daarnaast het solver-probleem
daarnaast rond M1 de gecorrigeerde getallen (oorspronkelijke getallen - een getal net kleiner dan het minimum) en daar nog eens naast de echte getallen.
daarnaast een logger om netjes mee te kunnen volgen wat er gebeurt.
Na iedere aanpassing wordt er onder M1 telkens die 2 tabellen met een kleine uitleg gekopieerd, ook om mee te kunnen volgen wat er gebeurt.
1 en ander mag achteraf wel komen te vervallen.

Die oranje M1 cel, daar is het mij om te doen, die is de som van de absolute afwijkingen tov het gewenste gemiddelde.
Voor jou is het eerder die groene M3-cel. Maar die 2 zijn met elkaar verwant.

Mijn grootste ergernis, is nu, dat solver voor 1 bepaalde run weer 100 sec (kolom BL) nodig heeft. Waarom is me een raadsel.
Stoeien met de parameters maxtime, precision en maxsubproblems maken niets uit.

Andere vraag is natuurlijk, had je de oorspronkelijke 84 getallen al in excel staan en hoe breng je die over naar Java of hoe werkte je precies.
Stond alles al in excel, dan moet je niet starten met kopieren en plakken, heen en terug en het tijdsverlies daarbij.

Nu is DE vraag, wat maakt voor jou het verschil tss die suboptimale oplossing van Java en deze betere oplossing van Excel ?
Heeft die een betere werking kwa vermogen of spanning of ... voor je batterijopstelling ?
Of is die financieel beter ?

Is dat ernstig, dan zou het te overwegen vallen om naar een andere methode over te stappen (= GAMS https://www.gams.com/latest/docs/UG_MAIN.html)
 

Bijlagen

  • RoosterOplossenMetSolver (1).xls
    170 KB · Weergaven: 18
Laatst bewerkt:
Dag Cow18,
Ik haal nu met je werkblad alles binnen in 22 sec... wat voor mij mooi is.

Heb eens gedacht om dat bestand op mijn bureaublad te plaatsen en vanuit Excel alles laten invullen...
Resultaat naar clipboard sturen en laten plakken in Excel... met +- 6 sec haal ik dan zeker alles binnen.
Maar ik leer liever je code in VBA. Die Java gebruik ik dus niet maar zoals jij wel erg benieuwd hoe ze het voor elkaar krijgen...

Als die GAMS met Excel kan werken dan maak je mij heel erg benieuwd.
Krijg nu juist 2 maanden les in Excel (geen VBA) en mijn leraar zei dat wat jij nu doet niet mogelijk is in Excel :)

Groetjes,
Leika
 
Die vertaalslag heen en terug naar Gams duurt gemiddeld iets meer dan 5 sec en dat doet hij nu 6 keer.
Zodoende is de oplossing op mijn computer is van een 32 sec.
Jij haalt nu blijkbaar al 22 sec. Dus ik werk nog ergens met een aftands model :confused:.
Wel wordt er niet meer gecorrigeerd om met kleine cijfers te kunnen werken.

Wat dat op jou computer zou kunnen betekenen, dat kan ik niet inschatten.
Misschien gelijk, misschien zelfs groter.

Het Gams-model kan ik hier niet zetten wegens niet passende extensie.
 

Bijlagen

  • Rooster.xls
    222 KB · Weergaven: 16
Laatst bewerkt door een moderator:
Dag Cow18,

Heb je bestand getest maar krijg die (nog) niet aan de praat maar blijf wel verder zoeken.
Die Gams kan je .txt extentie geven? Daarna geef ik hier de juiste…

Alvast dank voor dit bestand!

Groetjes,
Leika
 
Natuurlijk krijg je dat niet aan de praat, je zal eerst Gams moeten installeren en dan nog wat zaakjes aanpassen.

Vraag is nog altijd of het de moeite loont.
Je hebt me nog steeds niet overtuigd van het relatieve voordeel (financieel, operationeel, ... ) van die verbeterde oplossing van excel tov die suboptimale oplossing van java.
Code:
Sets             VolgNr   "de Volgnummers binnen een bepaalde pot"
                 PotNr    "de nummer van de pot"
;

parameter     Ideaal "de na te streven som"
              Waarden(VolgNr,PotNr) "de getallen volgens VolgNr en PotNr"
 ;

*aanmaken van een tekstbestand met daarin de plaatsen waar Gams zijn info moet zoeken binnen excel
$Onecho > InlezenExcel.txt
Set=Volgnr     rng=Gams!I1    rdim=1
set=PotNr      rng=Gams!I1            cdim=1
Par=Waarden    rng=Gams!I1    rdim=1  cdim=1
par=Ideaal rng=gams!B1 dim=0
$Offecho

*Gams de info laten ophalen van excel aan de hand van dat TXT-bestand
$call GDXXRW c:\Users\Eigenaar\Documents\Gamsdir\projdir\Rooster.xls Squeeze=N trace=3 @InlezenExcel.txt

*wegschrijven van de opgehaalde info naar een GDX-bestand dat Gams kan gebruiken
$GDXIN c:\Users\Eigenaar\Documents\Gamsdir\projdir\Rooster.gdx
$LOAD Volgnr PotNr Ideaal Waarden
$GDXIN


binary Variables B(VolgNr,PotNr) elementen die naar de andere pot gaan
;

Variables   UitPot(PotNr) "aantal per pot die naar de andere gaan"
            SomWeg(PotNr) "totaal die per pot verdwijnt naar de andere"
            Deltas(PotNr) "afwijking tov ideaal"
            SomDeltas "som van de absomlte deltas function"
            Totalen(PotNr) "huidig totaal in de pot"
;

positive variables
            PosDeltas(PotNr)
            NegDeltas(PotNr)
;

Equations   EqDeltaAbs Som van de absolute afwijkingen de optimalisatie
            EqUitPot(PotNr) aantallen die uit iedere pot verdwijnt
            EqSomWeg(PotNr)  Sommen uit de pot
            EqTotalen(PotNr) Wat er nu in de pot zit
            EqGelijk beide kanten moeten gelijk zijn
            EqDelta1
            EqDelta2
            EqAbs(Potnr)
            EqMaxB(VolgNr,PotNr)
;


EqMaxB(VolgNr,PotNr).. B(VolgNr,PotNr) =l= 1.1 ;
EqTotalen(PotNr)..   Totalen(PotNr) =E= sum(Volgnr, waarden(Volgnr,PotNr));
EqUitPot(PotNr)..  UitPot(PotNr) =E= sum(Volgnr, B(VolgNr,Potnr)) ;
EqSomWeg(PotNr)..  SomWeg(PotNr) =E= sum(Volgnr, waarden(Volgnr,PotNr)*B(VolgNr,Potnr))  ;
EqGelijk.. UitPot("pot1") =E= UitPot("pot2")  ;
EqDelta1 .. Deltas("pot1") =E= Totalen("pot1")-SomWeg("pot1")+SomWeg("pot2")-Ideaal ;
EqDelta2..  Deltas("pot2") =E= Totalen("pot2")+SomWeg("pot1")-SomWeg("pot2")-Ideaal  ;
EqAbs(potnr).. Deltas(PotNr) =E= PosDeltas(PotNr)- NegDeltas(PotNr)  ;
EqDeltaAbs..  SomDeltas =E=  PosDeltas("Pot1")+NegDeltas("Pot1")+PosDeltas("Pot2")+NegDeltas("Pot2") ;

model Uitwisselen /all/;
solve Uitwisselen using MIP minimizing SomDeltas   ;

display B.l, uitpot.l, somweg.l;
execute_unload 'roostertest.gdx',b,uitpot.l, somweg.l,somdeltas.l,PosDeltas.l,NegDeltas.L ;
execute "gdxxrw roostertest.gdx o=rooster2gams.xls var=B rng=A1 rdim=1  cdim=1"
 
Dag Cow18,

Had het dus getest met GAMS win64 25.1.3... en met RoosterTest4.lst op bureaublad.

Ik werk niet met die Java bestand en voor mijn part ben ik prima gesteld met je voorgaande Excel bestand.
Voor mij is het hobby en VBA leren, dus niks te maken met financieel of lichtsnelheid. :)
Kan het eventueel ook nog verder naar mijn hand zetten.
Heb je Excel file laten zien op school en die konden hun ogen niet geloven, hehe
Die leraar was zoals ik ook overtuigd dat dit max. met 15 getallen mogelijk is... :thumb:

Zal eens verder testen in weekend!

Groetjes,
Leika
 
Laatst bewerkt door een moderator:
roostertest4.gms
 
Status
Niet open voor verdere reacties.
Steun Ons

Nieuwste berichten

Terug
Bovenaan Onderaan