Question meaning:
A person starts to have an infinite amount of money and asks how much he can earn at most when buying a stock.
Requirements:
The number of stocks bought and sold per day is limited to bl and sl. The trading interval must exceed w + 1 day.
The maximum number of shares is p.
Solution:
Dp [I] [j] indicates the maximum benefit gained when j shares were held on the previous day.
Status transfer:
Dp [I-1] [j] When day I is not traded;
Dp [i-w-1] [k]-(j-k) on day I buy (j-k) * B [I] 0 = <k <= j // note that the I-w ---- I-1 cannot be traded on a daily basis.
When selling (k-j) shares, dp [i-w-1] [k] + (k-j) * s [I] j = <k <= p
When a j is fixed, dp [i-w-1] [k] + k * B [I] is fixed (k, j has a relationship), so monotonous queue optimization can be used.
Code:
<SPAN style = "FONT-SIZE: 18px ">#include <iostream> # include <cmath> # include <cstdio> # include <cstdlib> # include <string> # include <cstring> # include <algorithm> # include <vector> # include <map> # include <stack> # include <list> # include <queue> # define eps 1e-6 # define INF 0x1f1f1f1f # define PI acos (-1.0) # define ll _ int64 # define lson l, m, (rt <1) # define rson m + 1, r, (rt <1) | 1 using namespace std; /* freopen ("data. in "," r ", stdin); freopen (" data. out "," w ", stdout); */int dp [2200] [2200], B [2200], s [2200], bl [2200], sl [2200]; struct Node {int nu, mo;} myd [2200]; int main () {int w, t, p, ca; scanf ("% d ", & ca); while (ca --) {scanf ("% d", & t, & p, & w); for (int I = 1; I <= t; I ++) scanf ("% d", & B [I], & s [I], & bl [I], & sl [I]); memset (dp,-INF, sizeof (dp); for (int j = 1; j <= t; j ++) // All stocks are bought on the same day for (int I = 0; I <= min (bl [j], p); I ++) dp [j] [I] = max (dp [j] [I],-I * B [j]); for (int I = 2; I <= t; I ++) {dp [I] [0] = 0; for (int j = 0; j <= p; j ++) // No transaction dp [I] [j] = max (dp [I-1] [j], dp [I] [j]); if (I <w + 2) // cannot trade continue; int pre = i-w-1; int ss = 0, e =-1; for (int j = 0; j <= p; j ++) // buy {int tmp = dp [pre] [j] + j * B [I]; while (ss <= e & tmp> = myd [e]. mo) e --; struct Node te; te. nu = j, te.mo = tmp; myd [++ e] = te; while (ss <= e & j-myd [ss]. nu> bl [I]) ss ++; dp [I] [j] = max (dp [I] [j], myd [ss]. mo-j * B [I]);} ss = 0, e =-1; // memset (myd, 0, sizeof (myd )); for (int j = p; j> = 0; j --) // sell {int tmp = dp [pre] [j] + j * s [I]; while (ss <= e & tmp> = myd [e]. mo) e --; struct Node te; te. nu = j; te.mo = tmp; myd [++ e] = te; while (ss <= e & myd [ss]. nu-j> sl [I]) ss ++; dp [I] [j] = max (dp [I] [j], myd [ss]. mo-j * s [I]) ;}} int ans = 0; for (int I = 0; I <= p; I ++) ans = max (ans, dp [t] [I]); printf ("% d \ n", ans);} return 0 ;}</SPAN>