Exemple #1
0
        /// <summary>
        /// Conventional 2-approximation algorithm for 0-1KP
        /// Result, r holds to outcome that optimal solution, z* is less than or equal to 2r
        /// i.e. 2r provides upper bound for profit
        /// </summary>
        /// <returns></returns>
        public static int Conventional2Approx_KP(List <Item> items, Knapsack knapsack)
        {
            ItemGroup group = new ItemGroup();

            List <Item> sortedItems = UtilFunctions.SortByUnitProfitDescending(items);

            // Fill until we reach critical item
            foreach (Item item in sortedItems)
            {
                if (group.TotalWeight() + item.Weight <= knapsack.Capacity)
                {
                    group.AddItem(item);
                }
                else // we have reached critical item
                {
                    var criticalItem = item;

                    // 2-approximation solution is one with higher profit value of group or criticalItem
                    if (criticalItem.Value > group.TotalValue())
                    {
                        group = (ItemGroup) new ItemGroup().Add(criticalItem);
                    }

                    break;
                }
            }

            return(group.TotalValue());
        }
        private void WriteSolutionAndData(ItemGroup requiredValueGroup)
        {
            LogFile.WriteLine("Maximum value after choosing {0} of first {1} items at weight {2} is {3}",
                              _knapsack.AllowedItems,
                              _items.Count,
                              _knapsack.Capacity,
                              requiredValueGroup.TotalValue()
                              );
            LogFile.WriteLine("No of items: {0}", requiredValueGroup.ItemCount());
            LogFile.WriteLine("Item names: {0}", requiredValueGroup.ItemNames());
            LogFile.WriteLine("Total weight: {0}", requiredValueGroup.TotalWeight());
            LogFile.WriteLine("Total value: {0}", requiredValueGroup.TotalValue());

            Console.WriteLine("Maximum value after choosing {0} of first {1} items at weight {2} is {3}",
                              _knapsack.AllowedItems,
                              _items.Count,
                              _knapsack.Capacity,
                              requiredValueGroup.TotalValue()
                              );
            Console.WriteLine("No of items: {0}", requiredValueGroup.ItemCount());
            Console.WriteLine("Item names: {0}", requiredValueGroup.ItemNames());
            Console.WriteLine("Total weight: {0}", requiredValueGroup.TotalWeight());
            Console.WriteLine("Total value: {0}", requiredValueGroup.TotalValue());

            DumpArrayToLog(m => m.TotalValue());
            DumpArrayToLog(m => m.ItemCount());
        }
        public void CalculateRecursive()
        {
            int currentCapacity = _knapsack.Capacity;

            ItemGroup requiredValueGroup = GetMaxValue(_items.Count, currentCapacity, _knapsack.AllowedItems);

            // Actual solution is not simply finding a value at capacity and allowed items
            // because we are only solving for kKP (not E-kKP)
            // Actually want to find value at AllowedItems, but potentially at lower capacity, with ItemCount = AllowedItems
            while (requiredValueGroup.ItemCount() < _knapsack.AllowedItems)
            {
                if (--currentCapacity == 0)
                {
                    break;
                }

                requiredValueGroup = GetMaxValue(_items.Count, currentCapacity, _knapsack.AllowedItems);
            }

            if (currentCapacity == 0)
            {
                Console.WriteLine(
                    "There is no valid solution with capacity constraint of {0} and count constraint of {1}.",
                    _knapsack.Capacity, _knapsack.AllowedItems);

                return;
            }

            LogFile.WriteLine("Maximum value after choosing {0} of first {1} items at weight {2} is {3}",
                              _knapsack.AllowedItems,
                              _items.Count,
                              _knapsack.Capacity,
                              requiredValueGroup.TotalValue()
                              );
            LogFile.WriteLine("No of items: {0}", requiredValueGroup.ItemCount());
            LogFile.WriteLine("Item names: {0}", requiredValueGroup.ItemNames());
            LogFile.WriteLine("Total weight: {0}", requiredValueGroup.TotalWeight());
            LogFile.WriteLine("Total value: {0}", requiredValueGroup.TotalValue());

            Console.WriteLine("Maximum value after choosing {0} of first {1} items at weight {2} is {3}",
                              _knapsack.AllowedItems,
                              _items.Count,
                              _knapsack.Capacity,
                              requiredValueGroup.TotalValue()
                              );
            Console.WriteLine("No of items: {0}", requiredValueGroup.ItemCount());
            Console.WriteLine("Item names: {0}", requiredValueGroup.ItemNames());
            Console.WriteLine("Total weight: {0}", requiredValueGroup.TotalWeight());
            Console.WriteLine("Total value: {0}", requiredValueGroup.TotalValue());
        }
        private void WriteSolutionAndData()
        {
            bool exactSolutionExists = Exact_K_SolutionExists();

            if (exactSolutionExists)
            {
                ItemGroup maxProfitGroup = GetSolution(_knapsack.AllowedItems);

                Console.WriteLine("Solution exists for exactly {0} items", _knapsack.AllowedItems);
                Console.WriteLine("  No of items:  {0}", maxProfitGroup.ItemCount());
                Console.WriteLine("  Item names:   {0}", maxProfitGroup.ItemNames());
                Console.WriteLine("  Total weight: {0}", maxProfitGroup.TotalWeight());
                Console.WriteLine("  Total value:  {0}", maxProfitGroup.TotalValue());
            }

            ItemGroup optimalGroup = GetOptimalSolution();

            Console.WriteLine("Optimal value solution:");
            Console.WriteLine("  No of items:  {0}", optimalGroup.ItemCount());
            Console.WriteLine("  Item names:   {0}", optimalGroup.ItemNames());
            Console.WriteLine("  Total weight: {0}", optimalGroup.TotalWeight());
            Console.WriteLine("  Total value:  {0}", optimalGroup.TotalValue());

            //DumpArrayToLog(m => m.TotalValue());
            //DumpArrayToLog(m => m.ItemCount());
        }
Exemple #5
0
        /// <summary>
        /// Uses greedy algorithm to get approximation of highest value for profit
        /// </summary>
        /// <returns></returns>
        public static double LPRelaxedApprox_KP(List <Item> items, Knapsack knapsack)
        {
            ItemGroup group = new ItemGroup();

            List <Item> sortedItems = UtilFunctions.SortByUnitProfitDescending(items);

            Item   criticalItem         = new Item("", 0, 0);
            double criticalItemFraction = 0;

            // Fill until we reach critical item
            foreach (Item item in sortedItems)
            {
                if (group.TotalWeight() + item.Weight <= knapsack.Capacity)
                {
                    group.AddItem(item);
                }
                else // we have reached critical item
                {
                    criticalItem         = item;
                    criticalItemFraction = (knapsack.Capacity - group.TotalWeight()) / (double)criticalItem.Weight;
                    break;
                }
            }

            // Add fractional value of next item
            double maxProfitValue = group.TotalValue() + criticalItem.Value * criticalItemFraction;

            return(maxProfitValue);
        }
        public ItemGroup GetMaxValue(int forFirstN, int atWeight, int itemsChosen)
        {
            // value at 0 items or 0 weight, or 0 items chosen is 0
            if (forFirstN == 0 || atWeight <= 0 || itemsChosen == 0)
            {
                return(new ItemGroup());
            }

            // calculate the previous value
            if (_maxValues[forFirstN - 1, atWeight, itemsChosen] is null)
            {
                _maxValues[forFirstN - 1, atWeight, itemsChosen] = GetMaxValue(forFirstN - 1, atWeight, itemsChosen);
            }

            // if current item weight is greater than weight being calculated, don't add the value
            if (_items[forFirstN - 1].Weight > atWeight)
            {
                _maxValues[forFirstN, atWeight, itemsChosen] =
                    new ItemGroup(_maxValues[forFirstN - 1, atWeight, itemsChosen]);
            }
            else
            {
                ItemGroup withoutCurrentItem =
                    _maxValues[forFirstN - 1, atWeight - _items[forFirstN - 1].Weight, itemsChosen - 1];
                // if we haven't calculated max without current item, do it now
                if (withoutCurrentItem is null)
                {
                    withoutCurrentItem = GetMaxValue(forFirstN - 1, atWeight - _items[forFirstN - 1].Weight,
                                                     itemsChosen - 1);
                    _maxValues[forFirstN - 1, atWeight - _items[forFirstN - 1].Weight, itemsChosen - 1] =
                        withoutCurrentItem;
                }

                // add item to prev
                ItemGroup withCurrentItem = (ItemGroup) new ItemGroup(withoutCurrentItem).Add(_items[forFirstN - 1]);

                if (_maxValues[forFirstN - 1, atWeight, itemsChosen].TotalValue() >= withCurrentItem.TotalValue())
                {
                    _maxValues[forFirstN, atWeight, itemsChosen] =
                        new ItemGroup(_maxValues[forFirstN - 1, atWeight, itemsChosen]);
                }
                else
                {
                    _maxValues[forFirstN, atWeight, itemsChosen] = withCurrentItem;
                }
            }

            //LogFile.WriteLine("Maximum value after choosing {3} of first {0} items at weight {1} is {2}",
            //    forFirstN,
            //    atWeight,
            //    _maxValues[forFirstN, atWeight, itemsChosen].TotalValue(),
            //    itemsChosen);
            //LogFile.WriteLine("Items: {0}, Count: {1}, Total weight: {2}",
            //    _maxValues[forFirstN, atWeight, itemsChosen].ItemNames(),
            //    _maxValues[forFirstN, atWeight, itemsChosen].ItemCount(),
            //    _maxValues[forFirstN, atWeight, itemsChosen].TotalWeight());

            return(_maxValues[forFirstN, atWeight, itemsChosen]);
        }
Exemple #7
0
        private void WriteSolutionAndData()
        {
            ItemGroup requiredValueGroup = _maxProfitItemGroup[_items.Count, _knapsack.Capacity];

            Console.WriteLine("Maximum value for first {0} items at weight {1} is {2}", _items.Count, _knapsack.Capacity, requiredValueGroup.TotalValue());
            Console.WriteLine("No of items: {0}", requiredValueGroup.ItemCount());
            Console.WriteLine("Item names: {0}", requiredValueGroup.ItemNames());
            Console.WriteLine("Total weight: {0}", requiredValueGroup.TotalWeight());
            Console.WriteLine("Total value: {0}", requiredValueGroup.TotalValue());

            DumpArrayToLog(m => m.TotalValue());
            DumpArrayToLog(m => m.ItemCount());
        }
        private ItemGroup GetSolution(int numberOfItems)
        {
            ItemGroup maxProfitGroup = new ItemGroup();

            int itemsUpperBound = _maxProfitItemGroup.GetUpperBound(ItemsConsideredDimension);

            // find maximum value where all items in list considered and count = allowed items
            for (int weight = 0; weight <= _maxProfitItemGroup.GetUpperBound(WeightDimension); weight++)
            {
                if (_maxProfitItemGroup[itemsUpperBound, numberOfItems, weight].TotalValue() >
                    maxProfitGroup.TotalValue())
                {
                    maxProfitGroup = _maxProfitItemGroup[itemsUpperBound, numberOfItems, weight];
                }
            }

            return(maxProfitGroup);
        }
        private ItemGroup GetOptimalSolution()
        {
            ItemGroup maxProfitGroup = new ItemGroup();

            int itemsUpperBound = _maxProfitItemGroup.GetUpperBound(ItemsConsideredDimension);

            // find maximum value where all items in list considered
            for (int itemsChosen = _maxProfitItemGroup.GetUpperBound(ItemsChosenDimension); itemsChosen >= 0; itemsChosen--)
            {
                var solutionWithNItems = GetSolution(itemsChosen);

                if (solutionWithNItems.TotalValue() > maxProfitGroup.TotalValue())
                {
                    maxProfitGroup = solutionWithNItems;
                }
            }

            return(maxProfitGroup);
        }
Exemple #10
0
        public void CalculateRecursive()
        {
            if (Exact_K_SolutionExists())
            {
                ItemGroup maxProfitGroup = GetSolution(_knapsack.AllowedItems);

                Console.WriteLine("Solution exists for exactly {0} items", _knapsack.AllowedItems);
                Console.WriteLine("  No of items:  {0}", maxProfitGroup.ItemCount());
                Console.WriteLine("  Item names:   {0}", maxProfitGroup.ItemNames());
                Console.WriteLine("  Total weight: {0}", maxProfitGroup.TotalWeight());
                Console.WriteLine("  Total value:  {0}", maxProfitGroup.TotalValue());
            }

            ItemGroup optimalGroup = GetOptimalSolution();

            Console.WriteLine("Optimal value solution:");
            Console.WriteLine("  No of items:  {0}", optimalGroup.ItemCount());
            Console.WriteLine("  Item names:   {0}", optimalGroup.ItemNames());
            Console.WriteLine("  Total weight: {0}", optimalGroup.TotalWeight());
            Console.WriteLine("  Total value:  {0}", optimalGroup.TotalValue());
        }