1. 程式人生 > >CodeForces - 586C Gennady the Dentist 模擬(數學建模的感覺)

CodeForces - 586C Gennady the Dentist 模擬(數學建模的感覺)

開始 max cto problem vector color 人的 long class

http://codeforces.com/problemset/problem/586/C

題意:1~n個孩子排成一排看病。有這麽一個模型:孩子聽到前面的哭聲自信心就會減弱:第i個孩子看病時會發出v[i]的叫聲,他後面的那個人的自信心(不是p[i+1])會減少v[i],再後面一個會減少v[i]-1,如此下去直到聲音減弱為0.若某個人的自信心小於0,則他哭著跑回家,他身後的所有人會減掉d[i] 的自信。

題解:直接模擬很困難,有一個想法是將逃跑的孩子的聲音和將他嚇跑的(正在接診的)聲音疊加成s,省去了每次對逃跑的孩子後面所有人-d[i]的循環。

坑:

考慮如果第五個人走了,第六個人就會走到第四個人後面,這樣他就會減v[4]而不是v[4]-1,所以碰到已經跑了的小孩要跳過。

我一開始還忘了減d[i]...還想遞歸寫。。。

ac

#define  _CRT_SECURE_NO_WARNINGS
#include<cstdio>  
#include<algorithm>  
#include<iostream>
#include<string>
#include<vector>
#include<string.h>
using namespace std;
typedef long long ll;
const int maxn = 4000 + 5;
int v[maxn], d[maxn], p[maxn];
int e[maxn]; vector<int> ans; int n; void run(int j) { for (int k = j; k <= n; k++) { if (p[k] > 0 && p[k] - d[j] < 0) { run(k); } } } int main() { cin >> n; for (int i = 1; i <= n; i++) { cin >> v[i] >> d[i] >> p[i]; }
for (int i = 1; i <= n; i++) { if (p[i] >= 0) { ans.push_back(i); for (int j = i + 1; j <= n; j++) { p[j] -= v[i]; v[i]--; if (v[i] <= 0)break; } } else if (v[i]) { for (int j = i + 1; j <= n; j++) { p[j] -= d[i]; } } } cout << ans.size() << endl; for (int i = 0; i < ans.size(); i++) cout << ans[i] << ; cin >> n; }

CodeForces - 586C Gennady the Dentist 模擬(數學建模的感覺)