zoukankan      html  css  js  c++  java
  • HDU 3401 Trade dp 单调队列优化

    戳这里:3401

    题意:给出第 i 天的股票买卖价格(APi,BPi),以及每天股票买卖的数量上限(ASi,BSi),要求任两次交易需要间隔 W 天以上,即第 i 天交易,第 i + W + 1 天才能再交易,求最多能赚多少钱

    思路:dp[i][j] = max(dp[i - 1][j], max(dp[f][k] - (j - k) * APi[i]), max(dp[f][k] + (k - j) * BPi[i])); 从式子中观察出,若两天都持有股票数 j 时,之后的那一天所赚的钱不小于之前的那一天,所以可以省去对 f 的枚举,即:

    dp[i][j] = max(dp[i - 1][j], max(dp[i - 1 - w][k] - (j - k) * APi[i]), max(dp[i - 1 - w][k] + (k - j) * BPi[i]));

    观察到,决策2 j > k,决策3 k > j,且两天所持股票数相近的话,发生状态转移的可能性越大,故可以对 k 进行单调队列优化,

    决策2 化为 max(dp[i - 1 - w][k] + k * APi[i]) - j * APi[i]; (j >= k)

    决策3 化为 max(dp[i - 1 - w][k] + k * BPi[i]) - j * BPi[i]; (j <= k)

     1 #include "bits/stdc++.h"
     2 using namespace std;
     3 int t;
     4 int T, MaxP, W;
     5 int APi[2010], BPi[2010], ASi[2010], BSi[2010];
     6 
     7 int dp[2010][2010];
     8 struct Queue
     9 {
    10     int value, index;
    11 }q[2010], tmp;
    12 int front, rear;
    13 
    14 //dp[i][j] = max(dp[i - 1][j], max(dp[i - 1 - w][k] - (j - k) * APi[i]), max(dp[i - 1 - w][k] + (k - j) * BPi[i]));
    15 //决策2 化为 max(dp[i - 1 - w][k] + k * APi[i]) - j * APi[i]; (j >= k)
    16 //决策3 化为 max(dp[i - 1 - w][k] + k * BPi[i]) - j * BPi[i]; (j <= k)
    17 
    18 int main()
    19 {
    20     scanf("%d", &t);
    21     while(t--) {
    22         //初始化
    23         memset(dp, 0xf3, sizeof(dp));
    24         //输入
    25         int i, j, k;
    26         scanf("%d%d%d", &T, &MaxP, &W);
    27         for(i = 1; i <= T; ++i) {
    28             scanf("%d%d%d%d", &APi[i], &BPi[i], &ASi[i], &BSi[i]);
    29         }
    30         //处理前驱不完全的状态
    31         for(i = 1; i <= W + 1; ++i) {
    32             for(j = 0; j <= ASi[i]; ++j) {  //之前这里写成 j <= MaxP WA了一次
    33                 dp[i][j] = -j * APi[i];
    34             }
    35         }
    36         //从首个后继状态开始 dp
    37         for(i = 2; i <= T; ++i) {
    38             //决策1
    39             for(j = 0; j <= MaxP; ++j) {
    40                 dp[i][j] = max(dp[i][j], dp[i - 1][j]);
    41             }
    42             if(i <= W + 1) {
    43                 continue;
    44             }
    45             //决策2
    46             front = rear = 1;
    47             for(j = 0; j <= MaxP; ++j) {
    48                 tmp.index = j;
    49                 tmp.value = dp[i - 1 - W][j] + j * APi[i];
    50                 for( ; front < rear && tmp.value > q[rear - 1].value; --rear);
    51                 q[rear++] = tmp;
    52                 for( ; front < rear && q[front].index + ASi[i] < j; ++front);
    53                 dp[i][j] = max(dp[i][j], q[front].value - j * APi[i]);
    54             }
    55             //决策3
    56             front = rear = 1;
    57             for(j = MaxP; j >= 0; j--) {
    58                 tmp.index = j;
    59                 tmp.value = dp[i - 1 - W][j] + j * BPi[i];
    60                 for( ; front < rear && tmp.value > q[rear - 1].value; --rear);
    61                 q[rear++] = tmp;
    62                 for( ; front < rear && q[front].index - BSi[i] > j; ++front);
    63                 dp[i][j] = max(dp[i][j], q[front].value - j * BPi[i]);
    64             }
    65         }
    66         int res = 0;
    67         for(j = 0; j <= MaxP; ++j) {
    68             res = max(res, dp[T][j]);
    69         }
    70         printf("%d
    ", res);
    71     }
    72 }
  • 相关阅读:
    Hibernate save, saveOrUpdate, persist, merge, update 区别
    Eclipse下maven使用嵌入式(Embedded)Neo4j创建Hello World项目
    Neo4j批量插入(Batch Insertion)
    嵌入式(Embedded)Neo4j数据库访问方法
    Neo4j 查询已经创建的索引与约束
    Neo4j 两种索引Legacy Index与Schema Index区别
    spring data jpa hibernate jpa 三者之间的关系
    maven web project打包为war包,目录结构的变化
    创建一个maven web project
    Linux下部署solrCloud
  • 原文地址:https://www.cnblogs.com/AC-Phoenix/p/4487188.html
Copyright © 2011-2022 走看看