Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- // Knapsack DP is harder than FFT.
- #include<bits/stdc++.h>
- using namespace std;
- typedef int64_t ll; typedef pair<int,int> pii; typedef pair<ll,ll> pll;
- #define ff first
- #define ss second
- #define pb emplace_back
- #define FOR(i,n) for(int i=0;i<(n);++i)
- #define FOO(i,a,b) for(int i=(a);i<=int(b);++i)
- #define OOF(i,a,b) for(int i=(a);i>=int(b);--i)
- #define AI(x) begin(x),end(x)
- template<class I>bool chmax(I&a,I b){return a<b?(a=b,true):false;}
- template<class I>bool chmin(I&a,I b){return b<a?(a=b,true):false;}
- inline ll cdiv(ll x,ll m){return x/m+(x%m?(x<0)^(m>0):0);}
- #ifdef OWO
- #define safe cerr<<"\033[1;32m"<<__PRETTY_FUNCTION__<<" - "<<__LINE__<<" JIZZ\033[0m\n"
- #define debug(args...) SDF(#args, args)
- #define OIU(args...) ostream& operator<<(ostream&O,args)
- #define LKJ(S,B,E,F) template<class...T>OIU(S<T...>s){O<<B;int c=0;for(auto i:s)O<<(c++?", ":"")<<F;return O<<E;}
- LKJ(vector,'[',']',i)LKJ(deque,'[',']',i)LKJ(set,'{','}',i)LKJ(multiset,'{','}',i)LKJ(unordered_set,'{','}',i)LKJ(map,'{','}',i.ff<<':'<<i.ss)LKJ(unordered_map,'{','}',i.ff<<':'<<i.ss)
- template<class T,size_t N>OIU(array<T,N>a){return O<<vector<T>(AI(a));}template<class...T>OIU(pair<T...>p){return O<<'('<<p.ff<<','<<p.ss<<')';}template<class...T>OIU(tuple<T...>t){return O<<'(',apply([&O](T...s){int c=0;(...,(O<<(c++?", ":"")<<s));},t),O<<')';}
- template<class...T>void SDF(const char* s,T...a){int c=sizeof...(T);if(!c){cerr<<"\033[1;32mvoid\033[0m\n";return;}(cerr<<"\033[1;32m("<<s<<") = (",...,(cerr<<a<<(--c?", ":")\033[0m\n")));}
- #else
- #pragma GCC optimize("Ofast")
- #define safe ((void)0)
- #define debug(...) ((void)0)
- #endif
- const ll inf = 1e9, INF = 4e18;
- vector<int> f, d, t;
- ll check(int p, int lim){
- ll tot = 0;
- for(int i = 1; i <= p; ++i){
- if(d[i] == 0){
- if(f[i] >= lim) return INF;
- continue;
- }
- tot += cdiv(f[i] - lim + 1, d[i]);
- }
- return tot;
- }
- ll calc(int T, int p){
- int l = 0, r = 1e5 + 1, m;
- ll ret;
- while(l < r){
- // choose every value >= l
- m = (l + r) / 2;
- ret = check(p, m);
- if(ret > T) l = m + 1;
- else r = m;
- }
- ll ans = 0;
- for(int i = 1; i <= p; ++i){
- if(f[i] < l) continue;
- ll x = cdiv(f[i] - l + 1, d[i]);
- ans += (f[i] + (f[i] - d[i] * (x-1))) * x / 2;
- T -= x;
- }
- if(l - 1 > 0) ans += (l-1) * T;
- return ans;
- }
- void solve(int T, int n){
- f.assign(n + 1, 0);
- d.assign(n + 1, 0);
- t.assign(n + 1, 0);
- for(int i = 1; i <= n; ++i) cin >> f[i];
- for(int i = 1; i <= n; ++i) cin >> d[i];
- for(int i = 1; i <= n; ++i) cin >> t[i];
- ll ans = 0;
- for(int i = 1; i <= n; ++i){
- T -= t[i];
- if(T <= 0) break;
- chmax(ans, calc(T, i));
- }
- cout << ans << '\n';
- }
- int32_t main(){
- ios_base::sync_with_stdio(0);cin.tie(0);cout.tie(0);
- int T, n;
- while(cin >> T >> n) solve(T, n);
- return 0;
- }
Add Comment
Please, Sign In to add comment