首页 > 试题广场 >

【模板】01背包

[编程题]【模板】01背包
  • 热度指数:24592 时间限制:C/C++ 1秒,其他语言2秒 空间限制:C/C++ 256M,其他语言512M
  • 算法知识视频讲解
\hspace{15pt}你有一个背包,最大容量为 V。现有 n 件物品,第 i 件物品的体积为 v_i,价值为 w_i。研究人员提出以下两种装填方案:
{\hspace{20pt}}_\texttt{1.}\, 不要求装满背包,求能获得的最大总价值;
{\hspace{20pt}}_\texttt{2.}\, 要求最终恰好装满背包,求能获得的最大总价值。若不存在使背包恰好装满的装法,则答案记为 0

输入描述:
\hspace{15pt}第一行输入两个整数 nV\left(1\leqq n,V\leqq 10^3\right),分别表示物品数量与背包容量。 
\hspace{15pt}此后 n 行,第 i 行输入两个整数 v_i, w_i\left(1\leqq v_i,w_i\leqq 10^3\right),分别表示第 i 件物品的体积与价值。


输出描述:
\hspace{15pt}输出两行: 
{\hspace{20pt}}_\texttt{1.}\, 第一行输出方案 \texttt{1} 的答案;
{\hspace{20pt}}_\texttt{2.}\, 第二行输出方案 \texttt{2} 的答案(若无解输出 0)。
示例1

输入

3 5
2 10
4 5
1 4

输出

14
9

说明

\hspace{15pt}在该组样例中: 
\hspace{23pt}\bullet\, 选择第 1、第 3 件物品即可获得最大价值 10+4=14(未装满);
\hspace{23pt}\bullet\, 选择第 2、第 3 件物品可使背包体积 4+1=5 恰好装满且价值最大,为 5+4=9
示例2

输入

3 8
12 6
11 8
6 8

输出

8
0

说明

\hspace{15pt}装第三个物品时总价值最大但是不满,装满背包无解。

备注:
\hspace{15pt}要求 O(nV) 的时间复杂度,O(V) 空间复杂度。
clc 
clear

n_v_org = input('', 's');                           % 原始 输入

n_v_org = strsplit(n_v_org, ' ');                   % 拆分

n = str2double(n_v_org{1});                         % 物体 个数

T = str2double(n_v_org{2});                         % 背包 体积

prop_list = zeros(n, 2);                            % 物体 属性

for i = 1:n

    i_prop_org = input('', 's');

    i_prop_org = strsplit(i_prop_org, ' ');         % 拆分

    prop_list(i, 1) = str2double(i_prop_org{1});    % 1 物体 体积

    prop_list(i, 2) = str2double(i_prop_org{2});    % 2 物体 价值
end

prop_list;

% n = 3;                         % 物体 个数

% T = 5;                         % 背包 体积

% prop_list = [2 10
% 4 5
% 1 4];

dp_max_value = zeros(1, T+1);                       % 价值 表
dp_max_weight_value = -inf(1, T+1);                 % 价值 表
dp_max_weight_value(1) = 0;

for i = 1:n                                         % 物体 i

    i_t = prop_list(i, 1);                          % i 物体 体积

    i_v = prop_list(i, 2);                          % i 物体 价值

    for t = T+1:-1:i_t+1                            % 总 体积 t, 注意 小于 i 物体 体积 部分 不需要 计算, 加快 运行 效率
        
        if dp_max_value(1, t) < dp_max_value(1, t - i_t) + i_v
            
            dp_max_value(1, t) = dp_max_value(1, t - i_t) + i_v;
        end
        
        if dp_max_weight_value(1, t - i_t) > -1
            if dp_max_weight_value(1, t) < dp_max_weight_value(1, t - i_t) + i_v
    
                dp_max_weight_value(1, t) = dp_max_weight_value(1, t - i_t) + i_v;
            end
        end
        
        % % 上方 代码 可以 加快 计算
        % dp_max_value(1, t) = max([dp_max_value(1, t), dp_max_value(1, t - i_t) + i_v]);
        
        % if dp_max_weight_value(1, t - i_t) > -1
        %     dp_max_weight_value(1, t) = max([dp_max_weight_value(1, t), dp_max_weight_value(1, t - i_t) + i_v]);
        % end
    end
end

fprintf('%d\n%d', max(dp_max_value), max([dp_max_weight_value(T+1), 0]))



发表于 2024-01-28 19:58:07 回复(0)