Fractional Knapsack Problem - GeeksforGeeks

25 Apr, 2022
Given the weights and values of n items, we need to put these items in a knapsack of capacity W to get the maximum total value in the knapsack.
In the 0-1 Knapsack problem, we are not allowed to break items. We either take the whole item or don’t take it. 
Input: Items as (value, weight) pairs arr[] = {{60, 10}, {100, 20}, {120, 30}} Knapsack Capacity, W = 50; 
Output: Maximum possible value = 240 by taking items of weight 10 and 20 kg and 2/3 fraction of 30 kg. Hence total price will be 60+100+(2/3)(120) = 240
In Fractional Knapsack, we can break items for maximizing the total value of knapsack. This problem in which we can break an item is also called the fractional knapsack problem. 
Input : 
Same as above

Output :
Maximum possible value = 240
By taking full items of 10 kg, 20 kg and 
2/3rd of last item of 30 kg
A brute-force solution would be to try all possible subset with all different fraction but that will be too much time taking. 
An efficient solution is to use the Greedy approach. The basic idea of the greedy approach is to calculate the ratio value/weight for each item and sort the item on basis of this ratio. Then take the item with the highest ratio and add them until we can’t add the next item as a whole and at the end add the next item as much as we can. Which will always be the optimal solution to this problem.A simple code with our own comparison function can be written as follows, please see the sort function more closely, the third argument to sort function is our comparison function which sorts the item according to value/weight ratio in non-decreasing order. After sorting we need to loop over these items and add them in our knapsack satisfying above-mentioned criteria.
Below is the implementation of the above idea:
C++
Java
Python3
C#
// C/C++ program to solve fractional Knapsack Problem#include <bits/stdc++.h> using namespace std; // Structure for an item which stores weight and// corresponding value of Itemstruct Item {    int value, weight;     // Constructor    Item(int value, int weight)    {        this->value = value;        this->weight = weight;    }}; // Comparison function to sort Item according to val/weight// ratiobool cmp(struct Item a, struct Item b){    double r1 = (double)a.value / (double)a.weight;    double r2 = (double)b.value / (double)b.weight;    return r1 > r2;} // Main greedy function to solve problemdouble fractionalKnapsack(int W, struct Item arr[], int n){    //    sorting Item on basis of ratio    sort(arr, arr + n, cmp);     //    Uncomment to see new order of Items with their    //    ratio    /*    for (int i = 0; i < n; i++)    {        cout << arr[i].value << "  " << arr[i].weight << " :    "             << ((double)arr[i].value / arr[i].weight) <<    endl;    }    */     double finalvalue = 0.0; // Result (value in Knapsack)     // Looping through all Items    for (int i = 0; i < n; i++) {        // If adding Item won't overflow, add it completely        if (arr[i].weight <= W) {            W -= arr[i].weight;            finalvalue += arr[i].value;        }         // If we can't add current Item, add fractional part        // of it        else {            finalvalue += arr[i].value                          * ((double)W                             / (double)arr[i].weight);            break;        }    }     // Returning final value    return finalvalue;} // Driver codeint main(){    int W = 50; //    Weight of knapsack    Item arr[] = { { 60, 10 }, { 100, 20 }, { 120, 30 } };     int n = sizeof(arr) / sizeof(arr[0]);     // Function call    cout << "Maximum value we can obtain = "         << fractionalKnapsack(W, arr, n);    return 0;}
// Java program to solve fractional Knapsack Problemimport java.util.Arrays;import java.util.Comparator; // Greedy approachpublic class FractionalKnapSack {    // function to get maximum value    private static double getMaxValue(int[] wt, int[] val,                                      int capacity)    {        ItemValue[] iVal = new ItemValue[wt.length];         for (int i = 0; i < wt.length; i++) {            iVal[i] = new ItemValue(wt[i], val[i], i);        }         // sorting items by value;        Arrays.sort(iVal, new Comparator<ItemValue>() {            @Override            public int compare(ItemValue o1, ItemValue o2)            {                return o2.cost.compareTo(o1.cost);            }        });         double totalValue = 0d;         for (ItemValue i : iVal) {             int curWt = (int)i.wt;            int curVal = (int)i.val;             if (capacity - curWt >= 0) {                // this weight can be picked while                capacity = capacity - curWt;                totalValue += curVal;            }            else {                // item cant be picked whole                double fraction                    = ((double)capacity / (double)curWt);                totalValue += (curVal * fraction);                capacity                    = (int)(capacity - (curWt * fraction));                break;            }        }         return totalValue;    }     // item value class    static class ItemValue {        Double cost;        double wt, val, ind;         // item value function        public ItemValue(int wt, int val, int ind)        {            this.wt = wt;            this.val = val;            this.ind = ind;            cost = new Double((double)val / (double)wt);        }    }     // Driver code    public static void main(String[] args)    {        int[] wt = { 10, 40, 20, 30 };        int[] val = { 60, 40, 100, 120 };        int capacity = 50;         double maxValue = getMaxValue(wt, val, capacity);         // Function call        System.out.println("Maximum value we can obtain = "                           + maxValue);    }}
# Python3 program to solve fractional# Knapsack Problem  class ItemValue:     """Item Value DataClass"""     def __init__(self, wt, val, ind):        self.wt = wt        self.val = val        self.ind = ind        self.cost = val // wt     def __lt__(self, other):        return self.cost < other.cost # Greedy Approach  class FractionalKnapSack:     """Time Complexity O(n log n)"""    @staticmethod    def getMaxValue(wt, val, capacity):        """function to get maximum value """        iVal = []        for i in range(len(wt)):            iVal.append(ItemValue(wt[i], val[i], i))         # sorting items by value        iVal.sort(reverse=True)         totalValue = 0        for i in iVal:            curWt = int(i.wt)            curVal = int(i.val)            if capacity - curWt >= 0:                capacity -= curWt                totalValue += curVal            else:                fraction = capacity / curWt                totalValue += curVal * fraction                capacity = int(capacity - (curWt * fraction))                break        return totalValue  # Driver Codeif __name__ == "__main__":    wt = [10, 40, 20, 30]    val = [60, 40, 100, 120]    capacity = 50     # Function call    maxValue = FractionalKnapSack.getMaxValue(wt, val, capacity)    print("Maximum value in Knapsack =", maxValue) # This code is contributed by vibhu4agarwal
// C# program to solve fractional Knapsack Problemusing System;using System.Collections; class GFG {     // Class for an item which stores weight and    // corresponding value of Item    class item {        public int value;        public int weight;         public item(int value, int weight)        {            this.value = value;            this.weight = weight;        }    }     // Comparison function to sort Item according    // to val/weight ratio    class cprCompare : IComparer {        public int Compare(Object x, Object y)        {            item item1 = (item)x;            item item2 = (item)y;            double cpr1 = (double)item1.value                          / (double)item1.weight;            double cpr2 = (double)item2.value                          / (double)item2.weight;             if (cpr1 < cpr2)                return 1;             return cpr1 > cpr2 ? -1 : 0;        }    }     // Main greedy function to solve problem    static double FracKnapSack(item[] items, int w)    {         // Sort items based on cost per units        cprCompare cmp = new cprCompare();        Array.Sort(items, cmp);         // Traverse items, if it can fit,        // take it all, else take fraction        double totalVal = 0f;        int currW = 0;         foreach(item i in items)        {            float remaining = w - currW;             // If the whole item can be            // taken, take it            if (i.weight <= remaining) {                totalVal += (double)i.value;                currW += i.weight;            }             // dd fraction until we run out of space            else {                if (remaining == 0)                    break;                 double fraction                    = remaining / (double)i.weight;                totalVal += fraction * (double)i.value;                currW += (int)(fraction * (double)i.weight);            }        }        return totalVal;    }     // Driver code    static void Main(string[] args)    {        item[] arr = { new item(60, 10), new item(100, 20),                       new item(120, 30) };         Console.WriteLine("Maximum value we can obtain = "                          + FracKnapSack(arr, 50));    }} // This code is contributed by Mohamed Adel
Maximum value we can obtain = 240
As main time taking step is sorting, the whole problem can be solved in O(n log n) only. This article is contributed by Utkarsh Trivedi.
YouTubeGeeksforGeeks507K subscribersFractional Knapsack Problem | GeeksforGeeksWatch laterShareCopy linkInfoShoppingTap to unmuteIf playback doesn't begin shortly, try restarting your device.You're signed outVideos you watch may be added to the TV's watch history and influence TV recommendations. To avoid this, cancel and sign in to YouTube on your computer.CancelConfirmMore videosMore videosSwitch cameraShareInclude playlistAn error occurred while retrieving sharing information. Please try again later.Watch on0:000:000:00 / 7:20•Live•<div class="player-unavailable"><h1 class="message">An error occurred.</h1><div class="submessage"><a href="https://www.youtube.com/watch?v=m1p-eWxrt6g" target="_blank">Try watching this video on www.youtube.com</a>, or enable JavaScript if it is disabled in your browser.</div></div>
 Please write comments if you find anything incorrect, or you want to share more information about the topic discussed above.
Prashant Mishra 9
vibhu4agarwal
jigyansu
salonikyal
firoz_baba
mahmd3adel
adnanirshad158
rajatsingh0805
Fraction
knapsack
Greedy
Greedy
Writing code in comment?
Please use ide.geeksforgeeks.org,
generate link and share the link here.
Huffman Coding | Greedy Algo-3
Activity Selection Problem | Greedy Algo-1
Program for Shortest Job First (or SJF) CPU Scheduling | Set 1 (Non- preemptive)
Job Sequencing Problem
Difference between Prim's and Kruskal's algorithm for MST
Dijkstra’s Algorithm for Adjacency List Representation | Greedy Algo-8
Program for Least Recently Used (LRU) Page Replacement algorithm
Shortest Remaining Time First (Preemptive SJF) Scheduling Algorithm
Graph Coloring | Set 2 (Greedy Algorithm)
Program for Page Replacement Algorithms | Set 2 (FIFO)