Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/algorithm/10.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/vb.net/15.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Algorithm 具有连续(非独立)约束的背包_Algorithm_Dynamic Programming_Knapsack Problem - Fatal编程技术网

Algorithm 具有连续(非独立)约束的背包

Algorithm 具有连续(非独立)约束的背包,algorithm,dynamic-programming,knapsack-problem,Algorithm,Dynamic Programming,Knapsack Problem,我看着。然而,我正在解决一个稍微不同的问题,其中约束是预算,价格,是双精度的,而不是整数。所以我想知道如何修改它?Double是“连续的”,不像整数,我可以有1,2,3。。。。我想我不会做0.0,0.1,0.2 更新1 我想把double乘以100转换成int。货币只有小数点后两位。但这意味着价值范围将非常大 更新2 我需要解决的问题是: 项目具有价格(双倍)和满意度(整数)值。我有一个预算作为约束,我需要最大限度地满足价值 在youtube视频中,作者创建了两个2d数组,如int[numIte

我看着。然而,我正在解决一个稍微不同的问题,其中约束是预算,价格,是双精度的,而不是整数。所以我想知道如何修改它?Double是“连续的”,不像整数,我可以有1,2,3。。。。我想我不会做0.0,0.1,0.2

更新1

我想把double乘以100转换成int。货币只有小数点后两位。但这意味着价值范围将非常大

更新2

我需要解决的问题是:

项目具有价格(双倍)和满意度(整数)值。我有一个预算作为约束,我需要最大限度地满足价值

在youtube视频中,作者创建了两个2d数组,如int[numItems][possibleCapacity(weight)]。在这里,我不能,因为预算是双精度的而不是整数

让你的眼睛看看。 对不起,我没有评论权限

编辑1

你是说约束是预算而不是背包重量? 这仍然是一个背包问题

或者你是说你有分数而不是项目值作为整数(0-1背包问题)。那么贪婪的方法就行了

编辑2

如果我正确理解你的问题。。它说

我们有
n
种商品,从1到n。每种商品
i
都有一个值
vi
和一个价格
pi
。我们通常假设所有的值和价格都是非负的。预算是
B

该问题最常见的表述是
0-1背包问题
,该问题将每种物品的
xi
份数限制为零或一份。从数学上讲,0-1背包问题可以表示为:

         n
maximize E(vi.xi)
         i=i

           n
subject to E(pi.xi) <= B,         xi is a subset of {0,1}
           i=1
您甚至可以将实数转换为int,正如您所提到的


是的,值的范围非常大,你还必须理解背包是NP完全的,也就是说,没有有效的算法来解决这个问题。仅使用DP的
伪多项式
解决方案。请参阅和。

如果您想使用具有任意精度的浮点数(即,没有固定数量的小数),并且它们不是分数,则动态编程将不起作用

动态规划的基础是存储特定输入的先前计算结果。因此,如果使用具有任意精度的浮点数,那么对于每个可能的浮点数,实际上都需要无限的内存,当然,还要进行无限计算,这是不可能的,也是非最优的


但是,如果这些数字具有固定的精度(与货币一样,货币只有两个十进制数字),您可以通过将它们相乘(如您所述)将其转换为整数,然后像往常一样解决背包问题。

这不是您问题的答案,但也可能是您正在寻找的:

线性规划 我曾经编写过一个简单的代码来解决您描述的问题。它不使用背包算法,而是使用单纯形法

使用系统;
使用System.Collections.Generic;
使用System.Linq;
使用系统文本;
使用Microsoft.SolverFoundation.Common;
使用Microsoft.SolverFoundation.Services;
名称空间优化程序
{
类项目
{
公共字符串ItemName{get;set;}
公共双价{get;set;}
公共双满意{get;set;}
静态void Main(字符串[]参数)
{
//我们的数据、预算和项目,以及各自的满意度和价格值
双倍预算=100.00;
列表项=新列表()
{
新项目(){
ItemName=“产品1”,
价格=20.1,
满意度=2.01
},
新项目(){
ItemName=“产品2”,
价格=1.4,
满意度=0.14
},
新项目(){
ItemName=“产品3”,
价格=22.1,
满意度=2.21
}
};
//用于解决问题的变量。
SolverContext上下文=SolverContext.GetContext();
Model Model=context.CreateModel();
长期目标=0;
术语约束=0;
foreach(项目中的项目i)
{
决策决策=新决策(Domain.integernonegative,i.ItemName);
model.AddDecision(decision);//每个项都是一个决策-算法是否应该增加此项?
目标+=i.满意度*决策;//决策将包含数量。
约束+=i.价格*决策;
}

constraint=constraint您必须执行更新1中所说的内容:以美分表示预算和项目价格(假设我们谈论的是美元)。然后我们谈论的不是任意精度或连续数字。每个价格(和预算)将是一个整数,只是那个整数将代表美分

为了让事情变得更简单,我们假设预算为10美元。问题是背包容量必须包含以下所有值:

[0.00, 0.01, 0.02, 0.03, ..., 9.99, 10.00] 
这些值是两个多值。解决方案矩阵和保留矩阵的每一行都有1001列,因此您将无法手动解决问题(如果预算为数百万美元,即使是一台计算机也可能有困难),但这是原始问题固有的(您对此无能为力)

您的最佳选择是使用一些关于背包的现有代码,或者编写自己的代码(我不建议这样做)

如果您找不到关于背包的现有代码,并且熟悉Linux/Mac,我建议您安装(GLPK)并解决这个问题
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.SolverFoundation.Common;
using Microsoft.SolverFoundation.Services;

namespace LPOptimizer
{
    class Item
    {
        public String ItemName { get; set; }
        public double Price { get; set; }
        public double Satisfaction { get; set; }

        static void Main(string[] args)
        {
            //Our data, budget and items with respective satisfaction and price values
            double budget = 100.00;
            List<Item> items = new List<Item>()
            {
                new Item(){
                    ItemName="Product_1", 
                    Price=20.1, 
                    Satisfaction=2.01
                },
                new Item(){
                    ItemName="Product_2", 
                    Price=1.4, 
                    Satisfaction=0.14
                },
                new Item(){
                    ItemName="Product_3", 
                    Price=22.1, 
                    Satisfaction=2.21
                }
            };

            //variables for solving the problem.
            SolverContext context = SolverContext.GetContext();
            Model model = context.CreateModel();
            Term goal = 0; 
            Term constraint = 0; 

            foreach (Item i in items)
            {
                Decision decision = new Decision(Domain.IntegerNonnegative, i.ItemName);
                model.AddDecision(decision); //each item is a decision - should the algorithm increase this item or not?

                goal += i.Satisfaction * decision; //decision will contain quantity.
                constraint += i.Price * decision; 
            }

            constraint = constraint <= budget; //this now says: "item_1_price * item_1_quantity + ... + item_n_price * item_n_quantity <= budget";

            model.AddConstraints("Budget", constraint); 

            model.AddGoals("Satisfaction", GoalKind.Maximize, goal); //goal says: "Maximize: item_1_satisfaction * item_1_quantity + ... + item_n_satisfaction * item_n_quantity"

            Solution solution = context.Solve(new SimplexDirective());
            Report report = solution.GetReport();
            Console.Write("{0}", report);
            Console.ReadLine();
        }
    }
}
[0.00, 0.01, 0.02, 0.03, ..., 9.99, 10.00] 
Define K[0..M, 0..n] where K[j, i] = optimal value of items in knapsack of size j, using only items 1, ..., i

for j = 0 to M do K[j,0] = 0
for i = 1 to n do
    for j = 0 to M do
        //Default case: Do not take item i
        K[j,1] = K[j, i-1]
        if j >= w_i and v_i+K[j-w, i-1] > K[j, i] then
            //Take item i
            K[j,i] = v_i + K[j-w_i, i-1]
Define L[0..S, 0..N] where L[j, i] = minimal weight of items in knapsack of total value >= j, using only items 1, ..., i
and S = total value of all items

for j = 0 to S do L[j, 0] = 0
for i = 0 to n do
    for j = 0 to S do
        //Default case: Do not take item i
        L[j,i] = L[j, i-1]
        if j >= v_i and L[j-v_i, i-1] + w_i < L[j, i] then
            //Take item i
            L[j, i] = L[j -v_i, i-1] + w_i