Problem:
Problem B:
Restaurant
Steve runs a small restaurant in a city. Also, as he is the only cook in his restaurant, he cooks everything
ordered by customers.
Basically he attends to orders by
first-come-first-served
principle. He takes some prescribed time to
prepare each dish. As a customer can order more than one dish at a time, Steve starts his cooking with
the dish that takes the longest time to prepare. In case that there are two or more dishes that take
the same amount of time to prepare, he makes these dishes in the sequence as listed in the menu card
of his restaurant. Note that he does not care in which order these dishes have been ordered. When he
completes all dishes ordered by a customer, he immediately passes these dishes to the waitress and has
them served to the customer. Time for serving is negligible.
On the other hand, during his cooking for someone’s order, another customer may come and order dishes.
For his efficiency, he decided to prepare together multiple dishes of the same if possible. When he starts
cooking for new dishes, he looks over the orders accepted by that time (including the order accepted
exactly at that time if any), and counts the number of the same dishes he is going to cook next. Time
required for cooking is the same no matter how many dishes he prepare at once. Unfortunately, he has
only limited capacity in the kitchen, and hence it is sometimes impossible that the requested number of
dishes are prepared at once. In such cases, he just prepares as many dishes as possible.
Your task is to write a program that simulates the restaurant. Given a list of dishes in the menu card
and orders from customers with their accepted times, your program should output a list of times when
each customer is served.
Input
The input contains multiple data sets. Each data set is in the format below:
N M
Name
1
Limit
1
Time
1
...
Name
N
Limit
N
Time
N
T
1
K
1
Dish
1,1
. . .
Dish
1,
K
1
...
T
M
K
M
Dish
M
,1
. . .
Dish
M
,
K
M
Here,
N
(1 ≤
N
≤ 20) and
M
(1 ≤
M
≤ 100) specify the number of entries in the menu card and the
number of orders that Steve will receive, respectively; each
Name
i
is the name of a dish of the
i
-th entry
in the menu card, which consists of up to 20 alphabetical letters;
Limit
i
(1 ≤
Limit
i
≤ 10) is the number of dishes he can prepare at the same time;
Time
i
(1 ≤
Time
i
≤ 1000) is time required to prepare a dish
(or dishes) of the
i
-th entry;
T
j
(1 ≤
T
j
≤ 10000000) is the time when the
j
-th order is accepted;
K
j
(1 ≤
K
j
≤ 10) is the number of dishes in the
j
-th order; and each
Dish
j,k
represents a dish in the
j
-th
order.
You may assume that every dish in the orders is listed in the menu card, but you should note that each
order may contain multiple occurrences of the same dishes. The orders are given in ascending order by
T
j
, and no two orders are accepted at the same time.
The input is terminated with a line that contains two zeros. This is not part of data sets and hence
should not be processed.
Ou
...(truncated)

Submitted solutions:

code_snippet: #include<cstdio>
#include<cstdlib>
#include<cstring>
#include<cmath>
#include<iostream>
#include<string>
#include<vector>
#include<map>
#include<set>
#include<list>
#include<queue>
#include<deque>
#include<algorithm>
#include<numeric>
#include<utility>
#include<complex>
#include<functional>
 
using namespace std;

/* constant */

const int MAX_N = 20;
const int MAX_M = 100;

/* typedef */

typedef vector<int> vi;
typedef set<int> si;
typedef pair<int,int> pii;
typedef vector<pii> vpii;

struct Menu {
  int id, limit, time;
  string name;
  bool operator<(const Menu& m0) const {
    return time > m0.time || (time == m0.time && id < m0.id);
  }
  void print() {
    printf("Menu: id=%d, limit=%d, time=%d, name=%s\n",
	   id, limit, time, name.c_str());
  }
};

struct Order {
  int id, t, k, mnums[MAX_N];
  Order() { memset(mnums, 0, sizeof(mnums)); }
  void print() {
    printf("Order: id=%d, t=%d, k=%d: ", id, t, k);
    for (int i = 0; i < MAX_N; i++) {
      if (i > 0) putchar(',');
      printf("%d", mnums[i]);
    }
    putchar('\n');
  }
};

enum { C_IDLE, C_COOK, C_WAIT };
enum { E_ORDER, E_CFIN, E_CST};

struct Event {
  int t, ev, oid;
  Event() {}
  Event(int _t, int _ev, int _oid) : t(_t), ev(_ev), oid(_oid) {}
  bool operator>(const Event& e0) const {
    return t > e0.t || (t == e0.t && ev > e0.ev);
  }
  void print() { printf("Event: t=%d, ev=%d, oid=%d\n", t, ev, oid); }
};

/* global variables */

int n, m;
Menu menu[MAX_N];
Order orders[MAX_M];
int fts[MAX_M], omsums[MAX_N];

/* subroutines */

/* main */

int main() {
  for (bool first = true;; first = false) {
    cin >> n >> m;
    if (n == 0) break;

    for (int i = 0; i < n; i++) {
      cin >> menu[i].name >> menu[i].limit >> menu[i].time;
      menu[i].id = i;
    }
    sort(menu, menu + n);
    //for (int i = 0; i < n; i++) menu[i].print();
    
    for (int i = 0; i < m; i++) {
      cin >> orders[i].t >> orders[i].k;
      orders[i].id = i;
      for (int j = 0; j < orders[i].k; j++) {
	string mname;
	cin >> mname;
	for (int mi = 0; mi < n; mi++)
	  if (menu[mi].name == mname) {
	    orders[i].mnums[mi]++;
	    break;
	  }
      }
    }
    //for (int i = 0; i < m; i++) orders[i].print();

    priority_queue<Event, vector<Event>, greater<Event> > q;
    
    for (int i = 0; i < m; i++)
      q.push(Event(orders[i].t, E_ORDER, i));

    int cstat = C_IDLE, cmenu, cnum;
    vpii clist;
    si olist;

    memset(omsums, 0, sizeof(omsums));

    while (! q.empty()) {
      Event e = q.top();
      q.pop();
      //e.print();

      // order arrived
      if (e.ev == E_ORDER) {
	olist.insert(e.oid);

	for (int i = 0; i < n; i++)
	  omsums[i] += orders[e.oid].mnums[i];
	
	if (cstat == C_IDLE) {
	  cstat = C_WAIT;
	  q.push(Event(e.t, E_CST, -1));
	}
      }

      // finish cooking
      else if (e.ev == E_CFIN) {
	for (int i = 0; i < clist.size(); i++) {
	  int oid = clist[i].first;
	  int num = clist[i].second;
	  orders[oid].mnums[cmenu] -= num;
	  orders[oid].k -= num;
	  if (orders[oid].k == 0) {
	    olist.erase(oid);
	    fts[oid] = e.t;
	  }
	}

	omsums[cmenu] -= cnum;
	
	cstat = C_IDLE;
	if (! olist.empty()) {
	  cstat = C_WAIT;
	  q.push(Event(e.t, E_CST, -1));
	}
      }

      // start cooking
      else if (e.ev == E_CST) {
	if (! olist.empty()) {
	  int oid = *(olist.begin());
	  for (cmenu = 0; cmenu < n; cmenu++)
	    if (orders[oid].mnums[cmenu] > 0) break;

	  cnum = omsums[cmenu];
	  if (cnum > menu[cmenu].limit) cnum = menu[cmenu].limit;

	  clist.clear();
	  int num = cnum;

	  for (si::iterator oit = olist.begin();
	       num > 0 && oit != olist.end(); oit++) {
	    int oid = *oit;
	    int onum = orders[oid].mnums[cmenu];
	    if (onum > 0) {
	      if (num > onum) {
		clist.push_back(pii(oid, onum));
		num -= onum;
	      }
	      else {
		clist.push_back(pii(oid, num));
		num = 0;
	      }
	    }
	  }

	  cstat = C_COOK;
	  q.push(Event(e.t + menu[cmenu].time, E_CFIN, -1));
	}
	else {
	  cstat = C_IDLE;
	}
      }
    }

    if (! first) putchar('\n');
    
    for (int i = 0; i < m; i++) cout << fts[i] << endl;
  }

  return 0;
}
accuracy: 1
time_ms: 20
memory_kb: 1240
final_rank: 3

code_snippet: #include<iostream>
#include<map>
#include<set>
#include<algorithm>
#include<cmath>
#include<deque>
#include<vector>
#define REP(i,s,n) for(int i=s;i<n;i++)
#define rep(i,n) REP(i,0,n)
#define inf (1<<28)
#define MAX_N 21
#define MAX_M 101
using namespace std;
typedef pair<int,int> ii;


ii ps[MAX_N];
struct P
{
  int index;
  bool finish;
  P(int index=inf,bool finish=false):index(index),finish(finish){}
  bool operator < (const P& a)const
  {
    if(ps[index].second != ps[a.index].second)return ps[index].second > ps[a.index].second;
    return index < a.index;
  }
};


map<string,int> list;
string names[MAX_N];

ii order[MAX_M];
bool fin[MAX_M];
int ans[MAX_M];
vector<P> cust[MAX_M];
int N,M;

int main()
{
  bool f = true;
  while(cin >> N >> M,N|M)
    {
      if(!f)cout << endl;
      f = false;
      rep(i,N)
	{
	  cin >> names[i] >> ps[i].first >> ps[i].second;
	  list[names[i]] = i;
	}
      rep(i,M)cust[i].clear(),fin[i] = false,ans[i] = inf;
      rep(i,M)
	{
	  int k;
	  cin >> order[i].first >> k;
	  order[i].second = i;

	  rep(j,k)
	    {
	      string name;
	      cin >> name;
	      cust[i].push_back(P(list[name]));
	    }
	  sort(cust[i].begin(),cust[i].end());
	}

      sort(order,order+M);



      int phase = order[0].first;
      bool update = true;
      while(update)
	{
	  //cout << "phase : "<< phase << endl;
	  update = false;
	  int choice = inf;
	  rep(i,M)
	    {
	      int cur = order[i].second;
	      if(fin[cur])continue;
	      if(order[i].first > phase)continue;
	      rep(j,cust[cur].size())
		{
		  if(cust[cur][j].finish)continue;
		  update = true;
		  choice = cust[cur][j].index;
		  break;
		}
	      if(update)break;
	      fin[cur] = true;
	    }

    

	  if(!update)
	    {
	      rep(i,M)
		{
		  int cur = order[i].second;
		  if(fin[cur])continue;
		  phase = order[i].first;
		  update = true;
		  break;
		}
	      if(update)continue;
	      break;
	    }
	  //cout << "choice = " << names[choice] <<endl;
	  int S = ps[choice].first;


	  rep(i,M)
	    {
	      int cur = order[i].second;
	      if(fin[cur])continue;
	      if(order[i].first > phase)continue;
	      rep(j,cust[cur].size())
		{
		  if(!cust[cur][j].finish && S > 0 && cust[cur][j].index == choice)
		    {
		      cust[cur][j].finish = true;
		      S--;
		    }
		}
	      if(S <= 0)break;
	    }

	  phase += ps[choice].second;
	  rep(i,M)
	    {
	      int cur = order[i].second;
	      if(fin[cur])continue;
	      bool ok = true;
	      rep(j,cust[cur].size())
		{
		  if(!cust[cur][j].finish)
		    {
		      ok = false;
		      break;
		    }
		}
	      if(ok)ans[cur] = min(ans[cur],phase),fin[cur] = true;
	    }


	}

      rep(i,M)cout << ans[i] << endl;

    }
  return 0;
}
accuracy: 1
time_ms: 20
memory_kb: 1356
final_rank: 7

code_snippet: #include <iostream>
#include <sstream>
#include <string>
#include <algorithm>
#include <vector>
#include <stack>
#include <queue>
#include <set>
#include <map>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <cmath>
#include <cassert>

using namespace std;

#define FOR(i,k,n) for(int i=(k); i<(int)(n); ++i)
#define REP(i,n) FOR(i,0,n)
#define FORIT(i,c) for(__typeof((c).begin())i=(c).begin();i!=(c).end();++i)

template<class T> void debug(T begin, T end){ for(T i = begin; i != end; ++i) cerr<<*i<<" "; cerr<<endl; }
inline bool valid(int x, int y, int W, int H){ return (x >= 0 && y >= 0 && x < W && y < H); }

typedef long long ll;
const int INF = 100000000;
const double EPS = 1e-8;
const int MOD = 1000000007;
int dx[8] = {1, 0, -1, 0, 1, -1, -1, 1};
int dy[8] = {0, 1, 0, -1, 1, 1, -1, -1};
struct Event{
  // type 0 - order
  // type 1 - complete
  int type, time, dish, customer;
  Event(int ty, int t, int d, int c):
    type(ty), time(t), dish(d), customer(c) {}
  bool operator < (const Event& e) const {
    if(time != e.time) return time > e.time;
    if(type != e.type) return type > e.type;
    return dish > e.dish;
  }
};
struct Dish{
  string name;
  int limit, time;
  Dish() {}
  bool operator < (const Dish& d) const {
    return time > d.time;
  }
};

int main(){
  int N, M;
  bool first = true;
  while(cin >> N >> M && N){
    if(first) first = false;
    else cout << endl;
    vector<Dish> dishes(N);
    REP(i, N) cin >> dishes[i].name >> dishes[i].limit >> dishes[i].time;
    stable_sort(dishes.begin(), dishes.end());
    map<string, int> name_to_index;
    REP(i, N) name_to_index[dishes[i].name] = i;
    priority_queue<Event> que;
    REP(i, M){
      int T, K; cin >> T >> K;
      REP(j, K){
        string name; cin >> name;
        que.push(Event(0, T, name_to_index[name], i));
      }
    }
    vector<int> answer(M);
    vector<Event> cook_queue;
    int cooking = 0;
    while(!que.empty()){
      Event e = que.top(); que.pop();
      if(e.type == 0){
        //printf("customer %d order %s : time %d\n", e.customer, dishes[e.dish].name.c_str(), e.time);
        cook_queue.push_back(Event(0, 0, e.dish, e.customer));
      }else if(e.type == 1){
        //printf("customer %d's %s is finshed: time %d\n", e.customer, dishes[e.dish].name.c_str(), e.time);
        cooking --;
        answer[e.customer] = e.time;
      }
      if(cooking == 0 && !cook_queue.empty() && (que.empty() || e.time != que.top().time)){
        // new dish
        int new_dish = cook_queue[0].dish;
        for(vector<Event>::iterator it = cook_queue.begin(); it != cook_queue.end(); ){
          if(it->dish == new_dish){
            //printf("customer %d's %s is started : time %d -> %d\n", it->customer, dishes[it->dish].name.c_str(), e.time, e.time + dishes[new_dish].time);
            que.push(Event(1, e.time + dishes[new_dish].time, it->dish, it->customer));
            cooking++;
            it = cook_queue.erase(it);
            if(cooking >= dishes[new_dish].limit) break;
          }else{
            it++;
          }
        }
        assert(cooking <= dishes[new_dish].limit);
      }
    }
    assert(cooking == 0);
    REP(i, M) cout << answer[i] << endl;
  }
  return 0;
}
accuracy: 1
time_ms: 20
memory_kb: 1288
final_rank: 5

code_snippet: #include <cstdio>
#include <iostream>
#include <sstream>
#include <iomanip>
#include <algorithm>
#include <cmath>
#include <string>
#include <vector>
#include <list>
#include <queue>
#include <stack>
#include <set>
#include <map>
#include <bitset>
#include <numeric>
#include <climits>
#include <cfloat>
using namespace std;

int n, m;                     // 料理の種類数、注文の数

vector<string> name;          // 料理の名前
map<string, int> index;       // 料理の番号
vector<int> limit, makeTime;  // 一度に調理できる最大数、調理時間

vector<int> come, dishNum;    // 来店時間、各注文の料理の数
vector<vector<string> > dish; // 注文された料理の名前

class Data
{
public:
    int time, id;
    int a, b;
    Data(int time0, int id0, int a0, int b0){
        time = time0;
        id = id0;
        a = a0;
        b = b0;
    }
    bool operator< (const Data& d) const{
        if(time < d.time)
            return true;
        if(time == d.time){
            if(id == -1)
                return false;
            if(d.id == -1)
                return true;
            return make_pair(-makeTime[id], id) < make_pair(-makeTime[d.id], d.id);
        }
        return false;
    }
};

int main()
{
    bool isFirst = true;

    for(;;){
        cin >> n >> m;
        if(n == 0)
            return 0;

        if(isFirst)
            isFirst = false;
        else
            cout << endl;

        name.resize(n);
        limit.resize(n);
        makeTime.resize(n);
        index.clear();
        for(int i=0; i<n; ++i){
            cin >> name[i] >> limit[i] >> makeTime[i];
            index[name[i]] = i;
        }

        come.resize(m);
        dishNum.resize(m);
        dish.resize(m);
        multiset<Data> ms1, ms2;        // 各種イベント
        vector<vector<int> > finish(m); // 最後の料理が提供された時間
        for(int i=0; i<m; ++i){
            cin >> come[i] >> dishNum[i];
            dish[i].resize(dishNum[i]);
            finish[i].resize(dishNum[i], -1);
            for(int j=0; j<dishNum[i]; ++j){
                cin >> dish[i][j];
                ms1.insert(Data(come[i], index[dish[i][j]], i, j));
            }
        }

        vector<queue<pair<int, int> > > q(n); // 各料理の注文のキュー
        bool isFree = true;                   // 料理人が次の調理を始められるかどうか
        while(!ms1.empty()){
            int time = ms1.begin()->time;
            while(!ms1.empty() && time == ms1.begin()->time){
                Data d = *ms1.begin();
                ms1.erase(ms1.begin());

                if(d.id == -1){
                    isFree = true;
                }else{
                    q[d.id].push(make_pair(d.a, d.b));
                    ms2.insert(d);
                }
            }

            while(isFree && !ms2.empty()){
                Data d = *ms2.begin();
                ms2.erase(ms2.begin());

                if(finish[d.a][d.b] == -1){
                    int rest = limit[d.id];
                    while(rest > 0 && !q[d.id].empty()){
                        int a = q[d.id].front().first;
                        int b = q[d.id].front().second;
                        q[d.id].pop();

                        if(finish[a][b] == -1){
                            finish[a][b] = time + makeTime[d.id];
                            -- rest;
                        }
                    }
                    isFree = false;
                    ms1.insert(Data(time + makeTime[d.id], -1, -1, -1));
                }
            }
        }

        for(int i=0; i<m; ++i)
            cout << *max_element(finish[i].begin(), finish[i].end()) << endl;
    }
}
accuracy: 1
time_ms: 20
memory_kb: 1396
final_rank: 8

code_snippet: #include<queue>
#include<cstdio>
#include<cstring>
#include<algorithm>

#define rep(i,n) for(int i=0;i<(n);i++)

using namespace std;

struct menu{
	char name[21];
	int lim,t;
};

int n;
menu M[20];

bool cmp(int a,int b){
	return M[a].t>M[b].t || M[a].t==M[b].t && a<b;
}

int main(){
	for(int test=0,m;scanf("%d%d",&n,&m),n;test++){
		if(test>0) puts("");

		rep(i,n) scanf("%s%d%d",&M[i].name,&M[i].lim,&M[i].t);

		pair< int,vector<int> > order[100]; // <到着時刻,注文内容>
		rep(i,m){
			int k; scanf("%d%d",&order[i].first,&k);
			order[i].second.resize(k);
			rep(j,k){
				char name[21]; scanf("%s",name);
				rep(l,n) if(strcmp(name,M[l].name)==0) { order[i].second[j]=l; break; }
			}
			sort(order[i].second.begin(),order[i].second.end(),cmp);
		}

		int fin[100]={},ans[100];

		deque< pair<int,int> > wait; // <注文した人,調理待ちの料理>
		int cooking=0; // 今調理中かどうか
		priority_queue< pair<int,int> > Q; // <-time,event_type>
		rep(i,m) Q.push(make_pair(-order[i].first,i+1));
		while(!Q.empty()){
			int t=-Q.top().first,type=Q.top().second; Q.pop();

			// 来客
			if(type>0){
				type--;

				const vector<int> &O=order[type].second;
				rep(i,O.size()) wait.push_back(make_pair(type,O[i]));
			}
			// 料理ができた
			else{
				type*=-1;
				type--;

				fin[type]++;
				if(fin[type]==order[type].second.size()) ans[type]=t;
				cooking--;
			}

			if(cooking==0 && !wait.empty()){
				int a=wait.front().first,menuid=wait.front().second; wait.pop_front();
				Q.push(make_pair(-(t+M[menuid].t),-(a+1)));
				cooking++;

				int cnt=1;
				rep(i,wait.size()) if(wait[i].second==menuid && cnt<M[menuid].lim) {
					Q.push(make_pair(-(t+M[menuid].t),-(wait[i].first+1)));
					wait.erase(wait.begin()+i);
					i--;
					cnt++;
					cooking++;
				}
			}
		}

		rep(i,m) printf("%d\n",ans[i]);
	}

	return 0;
}
accuracy: 1
time_ms: 10
memory_kb: 0
final_rank: 1

code_snippet: #include <iostream>
#include <vector>
#include <queue>
#include <map>
#include <set>
#include <algorithm>
#include <string>

using namespace std;

struct Dish{
    string name;
    int time;
    int limit;
    int orderTime;
    int dishIdx;
    int whois;
    int ordNum;
    Dish(){}
    Dish(string _name,int _time,int _limit,int _orderTime,int _dishIdx,int _whois,int _ordNum){
        name=_name;
        time=_time;
        limit=_limit;
        orderTime=_orderTime;
        dishIdx=_dishIdx;
        whois=_whois;
        ordNum=_ordNum;
    }
    bool operator<(const Dish&dh)const{
        if(dh.orderTime!=orderTime)return dh.orderTime>this->orderTime;
        else if(dh.time!=this->time)return dh.time<this->time;
        else if(dh.dishIdx!=this->dishIdx)return dh.dishIdx>this->dishIdx;
        else if(dh.whois!=this->whois)return dh.whois>this->whois;
        return dh.ordNum<this->ordNum;
    }
};
struct Event{
    int time;
    int idx;
    int dishIdx;
    int kind;
    vector<int> who;
    Event(){}
    Event(int _time,int _idx,int _dishIdx,int _kind){
        time=_time;
        idx=_idx;
        dishIdx=_dishIdx;
        kind=_kind;
    }
    bool operator<(const Event&e)const{
        if(e.time!=this->time)return e.time<this->time;
        return (e.kind<this->kind);
    }
};

set<Dish> waitDish;
int N,M;
Dish ds[101];
map<string,int> ms;
int T[101];
int K[101];
int leftDish[101];
int finTimes[101];
bool need[100001];
vector<string> order[101];

int main(){
    bool fst=true;
    while(cin>>N>>M&&(N|M)){
        if(fst)fst=false;
        else cout<<endl;
        waitDish.clear();
        ms.clear();
        for(int i=0;i<N;i++){
            cin>>ds[i].name>>ds[i].limit>>ds[i].time;
            ms[ds[i].name]=i;
            ds[i].dishIdx=i;
        }
        for(int i=0;i<M;i++){
            order[i].clear();
            cin>>T[i];
            cin>>K[i];
            leftDish[i]=K[i];
            for(int j=0;j<K[i];j++){
                string str;
                cin>>str;
                order[i].push_back(str);
            }
        }
        priority_queue<Event> pq;
        bool isCook=false;
        for(int i=0;i<M;i++){
            pq.push(Event(T[i],i,0,0));
        }
        while(pq.size()){
            Event e=pq.top();pq.pop();
            if(e.kind==0){
                for(int j=0;j<K[e.idx];j++){
                    int dk=ms[order[e.idx][j]];
                    Dish tmp=ds[dk];
                    tmp.whois=e.idx;
                    tmp.orderTime=e.time;
                    tmp.ordNum=j;
                    waitDish.insert(tmp);
                }
                Event ne=Event(e.time,0,0,2);
                pq.push(ne);
            }
            else if(e.kind==1){
                int dkind=e.idx;
                for(int i=0;i<e.who.size();i++){
                    int user=e.who[i];
                    leftDish[user]--;
                    if(leftDish[user]==0)
                        finTimes[user]=e.time;
                }
                isCook=false;
                Event ne=Event(e.time,0,0,2);
                pq.push(ne);
            }
            else{
                if(isCook||waitDish.size()==0)continue;
                isCook=true;
                Dish d=*(waitDish.begin());
                int lim=(waitDish.begin())->limit;
                Event ne=Event(e.time+(waitDish.begin())->time,0,d.dishIdx,1);
                vector<Dish> tmp;
                for(set<Dish>::iterator it=waitDish.begin();it!=waitDish.end();it++)
                    tmp.push_back(*it);
                vector<int> idxs;
                for(int i=0;i<tmp.size();i++){
                    if(lim>0&&tmp[i].dishIdx==d.dishIdx){
                        ne.who.push_back(tmp[i].whois);
                        lim--;
                    }
                    else idxs.push_back(i);
                }
                waitDish.clear();
                for(int i=0;i<idxs.size();i++){
                    int cur=idxs[i];
                    waitDish.insert(tmp[cur]);
                }
                pq.push(ne);
            }
        }
         for(int i=0;i<M;i++)
            cout<<finTimes[i]<<endl;
    }
    return 0;
}
accuracy: 1
time_ms: 280
memory_kb: 0
final_rank: 6

code_snippet: #include <iostream>
#include <vector>
#include <queue>
#include <map>
#include <set>
#include <algorithm>
#include <string>

using namespace std;

struct Dish{
    string name;
    int time;
    int limit;
    int orderTime;
    int dishIdx;
    int whois;
    int ordNum;
    bool operator<(const Dish&dh)const{
        if(dh.orderTime!=orderTime)return dh.orderTime>this->orderTime;
        else if(dh.time!=this->time)return dh.time<this->time;
        else if(dh.dishIdx!=this->dishIdx)return dh.dishIdx>this->dishIdx;
        else if(dh.whois!=this->whois)return dh.whois>this->whois;
        return dh.ordNum<this->ordNum;
    }
};
struct Event{
    int time;
    int idx;
    int dishIdx;
    int kind;
    vector<int> who;
    bool operator<(const Event&e)const{
        if(e.time!=this->time)return e.time<this->time;
        return (e.kind<this->kind);
    }
};

set<Dish> waitDish;
int N,M;
Dish ds[101];
map<string,int> ms;
int T[101];
int K[101];
int leftDish[101];
int finTimes[101];
bool need[100001];
vector<string> order[101];

int main(){
    bool fst=true;
    while(cin>>N>>M&&(N|M)){
        if(fst)fst=false;
        else cout<<endl;
        waitDish.clear();
        ms.clear();
        for(int i=0;i<N;i++){
            cin>>ds[i].name>>ds[i].limit>>ds[i].time;
            ms[ds[i].name]=i;
            ds[i].dishIdx=i;
        }
        for(int i=0;i<M;i++){
            order[i].clear();
            cin>>T[i];
            cin>>K[i];
            leftDish[i]=K[i];
            for(int j=0;j<K[i];j++){
                string str;
                cin>>str;
                order[i].push_back(str);
            }
        }
        priority_queue<Event> pq;
        bool isCook=false;
        for(int i=0;i<M;i++){
            Event e;
            e.kind=0;
            e.idx=i;
            e.time=T[i];
            pq.push(e);
        }
        while(pq.size()){
            Event e=pq.top();pq.pop();
            if(e.kind==0){
                for(int j=0;j<K[e.idx];j++){
                    int dk=ms[order[e.idx][j]];
                    Dish tmp=ds[dk];
                    tmp.whois=e.idx;
                    tmp.orderTime=e.time;
                    tmp.ordNum=j;
                    waitDish.insert(tmp);
                }
                Event ne;
                ne.time=e.time;
                ne.kind=2;
                pq.push(ne);
            }
            else if(e.kind==1){
                int dkind=e.idx;
                for(int i=0;i<e.who.size();i++){
                    int user=e.who[i];
                    leftDish[user]--;
                    if(leftDish[user]==0){
                        finTimes[user]=e.time;
                    }
                }
                isCook=false;
                Event ne;
                ne.time=e.time;
                ne.kind=2;
                pq.push(ne);
            }
            else{
                if(isCook||waitDish.size()==0)continue;
                isCook=true;
                Dish d=*(waitDish.begin());
                int lim=(waitDish.begin())->limit;
                Event ne;ne.kind=1;ne.dishIdx=d.dishIdx;
                ne.time=e.time+(waitDish.begin())->time;
                vector<Dish> tmp;
                for(set<Dish>::iterator it=waitDish.begin();it!=waitDish.end();it++){
                    tmp.push_back(*it);
                }
                vector<int> idxs;
                for(int i=0;i<tmp.size();i++){
                    if(lim>0&&tmp[i].dishIdx==d.dishIdx){
                        ne.who.push_back(tmp[i].whois);
                        lim--;
                    }
                    else idxs.push_back(i);
                }
                waitDish.clear();
                for(int i=0;i<idxs.size();i++){
                    int cur=idxs[i];
                    waitDish.insert(tmp[cur]);
                }
                pq.push(ne);
            }
        }
         for(int i=0;i<M;i++)
            cout<<finTimes[i]<<endl;
    }
    return 0;
}
accuracy: 1
time_ms: 280
memory_kb: 1048
final_rank: 10

code_snippet: #include <iostream>
#include <vector>
#include <queue>
#include <map>
#include <set>
#include <algorithm>
#include <string>

using namespace std;

struct Dish{
    string name;
    int time;
    int limit;
    int orderTime;
    int dishIdx;
    int whois;
    int ordNum;
    bool operator<(const Dish&dh)const{
        if(dh.orderTime!=orderTime)return dh.orderTime>this->orderTime;
        else if(dh.time!=this->time)return dh.time<this->time;
        else if(dh.dishIdx!=this->dishIdx)return dh.dishIdx>this->dishIdx;
        else if(dh.whois!=this->whois)return dh.whois>this->whois;
        return dh.ordNum<this->ordNum;
    }
};
struct Event{
    int time;
    int idx;
    int dishIdx;
    int kind;
    vector<int> who;
    bool operator<(const Event&e)const{
        if(e.time<this->time)return true;
        else if(e.time>this->time)return false;
        return (e.kind<this->kind);
    }
};

set<Dish> waitDish;
int N,M;
Dish ds[101];
map<string,int> ms;
int T[101];
int K[101];
int leftDish[101];
int finTimes[101];
bool need[100001];
vector<string> order[101];

int main(){
    bool fst=true;
    while(cin>>N>>M&&(N|M)){
        if(fst)fst=false;
        else cout<<endl;
        waitDish.clear();
        ms.clear();
        for(int i=0;i<N;i++){
            cin>>ds[i].name>>ds[i].limit>>ds[i].time;
            ms[ds[i].name]=i;
            ds[i].dishIdx=i;
        }
        for(int i=0;i<M;i++){
            order[i].clear();
            cin>>T[i];
            cin>>K[i];
            leftDish[i]=K[i];
            for(int j=0;j<K[i];j++){
                string str;
                cin>>str;
                order[i].push_back(str);
            }
        }
        priority_queue<Event> pq;
        bool isCook=false;
        for(int i=0;i<M;i++){
            Event e;
            e.kind=0;
            e.idx=i;
            e.time=T[i];
            pq.push(e);
        }
        while(pq.size()){
            Event e=pq.top();pq.pop();
            if(e.kind==0){
                for(int j=0;j<K[e.idx];j++){
                    int dk=ms[order[e.idx][j]];
                    Dish tmp=ds[dk];
                    tmp.whois=e.idx;
                    tmp.orderTime=e.time;
                    tmp.ordNum=j;
                    waitDish.insert(tmp);
                }
                Event ne;
                ne.time=e.time;
                ne.kind=2;
                pq.push(ne);
            }
            else if(e.kind==1){
                int dkind=e.idx;
                for(int i=0;i<e.who.size();i++){
                    int user=e.who[i];
                    leftDish[user]--;
                    if(leftDish[user]==0){
                        finTimes[user]=e.time;
                    }
                }
                isCook=false;
                Event ne;
                ne.time=e.time;
                ne.kind=2;
                pq.push(ne);
            }
            else{
                if(isCook||waitDish.size()==0)continue;
                isCook=true;
                Dish d=*(waitDish.begin());
                int lim=(waitDish.begin())->limit;
                Event ne;ne.kind=1;ne.dishIdx=d.dishIdx;
                ne.time=e.time+(waitDish.begin())->time;
                vector<Dish> tmp;
                for(set<Dish>::iterator it=waitDish.begin();it!=waitDish.end();it++){
                    tmp.push_back(*it);
                }
                vector<int> idxs;
                for(int i=0;i<tmp.size();i++){
                    if(lim>0&&tmp[i].dishIdx==d.dishIdx){
                        ne.who.push_back(tmp[i].whois);
                        lim--;
                    }
                    else idxs.push_back(i);
                }
                waitDish.clear();
                for(int i=0;i<idxs.size();i++){
                    int cur=idxs[i];
                    waitDish.insert(tmp[cur]);
                }
                pq.push(ne);
            }
        }
         for(int i=0;i<M;i++)
            cout<<finTimes[i]<<endl;
    }
    return 0;
}
accuracy: 1
time_ms: 280
memory_kb: 1048
final_rank: 10

code_snippet: #include <iostream>
#include <vector>
#include <queue>
#include <map>
#include <set>
#include <algorithm>
#include <string>

using namespace std;

struct Dish{
    string name;
    int time;
    int limit;
    int orderTime;
    int dishIdx;
    int whois;
    int ordNum;
    bool operator<(const Dish&dh)const{
        if(dh.orderTime>this->orderTime)return true;
        else if(dh.orderTime<this->orderTime)return false;
        else if(dh.time<this->time)return true;
        else if(dh.time>this->time)return false;
        else if(dh.dishIdx>this->dishIdx)return true;
        else if(dh.dishIdx<this->dishIdx)return false;
        else if(dh.whois>this->whois)return true;
        else if(dh.whois<this->whois)return false;
        return dh.ordNum<this->ordNum;
    }
};
struct Event{
    int time;
    int idx;
    int dishIdx;
    int kind;
    vector<int> who;
    bool operator<(const Event&e)const{
        if(e.time<this->time)return true;
        else if(e.time>this->time)return false;
        return (e.kind<this->kind);
    }
};

set<Dish> waitDish;
int N,M;
Dish ds[101];
map<string,int> ms;
int T[101];
int K[101];
int leftDish[101];
int finTimes[101];
bool need[100001];
vector<string> order[101];

int main(){
    bool fst=true;
    while(cin>>N>>M&&(N|M)){
        if(fst)fst=false;
        else cout<<endl;
        waitDish.clear();
        ms.clear();
        for(int i=0;i<N;i++){
            cin>>ds[i].name>>ds[i].limit>>ds[i].time;
            ms[ds[i].name]=i;
            ds[i].dishIdx=i;
        }
        for(int i=0;i<M;i++){
            order[i].clear();
            cin>>T[i];
            cin>>K[i];
            leftDish[i]=K[i];
            for(int j=0;j<K[i];j++){
                string str;
                cin>>str;
                order[i].push_back(str);
            }
        }
        priority_queue<Event> pq;
        bool isCook=false;
        for(int i=0;i<M;i++){
            Event e;
            e.kind=0;
            e.idx=i;
            e.time=T[i];
            pq.push(e);
        }
        while(pq.size()){
            Event e=pq.top();pq.pop();
            if(e.kind==0){
                for(int j=0;j<K[e.idx];j++){
                    int dk=ms[order[e.idx][j]];
                    Dish tmp=ds[dk];
                    tmp.whois=e.idx;
                    tmp.orderTime=e.time;
                    tmp.ordNum=j;
                    waitDish.insert(tmp);
                }
                Event ne;
                ne.time=e.time;
                ne.kind=2;
                pq.push(ne);
            }
            else if(e.kind==1){
                int dkind=e.idx;
                for(int i=0;i<e.who.size();i++){
                    int user=e.who[i];
                    leftDish[user]--;
                    if(leftDish[user]==0){
                        finTimes[user]=e.time;
                    }
                }
                isCook=false;
                Event ne;
                ne.time=e.time;
                ne.kind=2;
                pq.push(ne);
            }
            else{
                if(isCook||waitDish.size()==0)continue;
                isCook=true;
                Dish d=*(waitDish.begin());
                int lim=(waitDish.begin())->limit;
                Event ne;ne.kind=1;ne.dishIdx=d.dishIdx;
                ne.time=e.time+(waitDish.begin())->time;
                vector<Dish> tmp;
                for(set<Dish>::iterator it=waitDish.begin();it!=waitDish.end();it++){
                    tmp.push_back(*it);
                }
                vector<int> idxs;
                for(int i=0;i<tmp.size();i++){
                    if(lim>0&&tmp[i].dishIdx==d.dishIdx){
                        ne.who.push_back(tmp[i].whois);
                        lim--;
                    }
                    else idxs.push_back(i);
                }
                waitDish.clear();
                for(int i=0;i<idxs.size();i++){
                    int cur=idxs[i];
                    waitDish.insert(tmp[cur]);
                }
                pq.push(ne);
            }
        }
         for(int i=0;i<M;i++)
            cout<<finTimes[i]<<endl;
    }
    return 0;
}
accuracy: 1
time_ms: 280
memory_kb: 1048
final_rank: 10

code_snippet: #include <iostream>
#include <vector>
#include <queue>
#include <map>
#include <set>
#include <algorithm>
#include <string>

using namespace std;

struct Dish{
    string name;
    int time;
    int limit;
    int orderTime;
    int idx;
    int whois;
    int ordNum;
    bool operator<(const Dish&dh)const{
        if(dh.orderTime>this->orderTime)return true;
        else if(dh.orderTime<this->orderTime)return false;
        else if(dh.time<this->time)return true;
        else if(dh.time>this->time)return false;
        else if(dh.idx>this->idx)return true;
        else if(dh.idx<this->idx)return false;
        else if(dh.whois>this->whois)return true;
        else if(dh.whois<this->whois)return false;
        return dh.ordNum<this->ordNum;
    }
};
struct Event{
    int time;
    int idx;
    int kind;
    vector<int> who;
    bool operator<(const Event&e)const{
        if(e.time<this->time)return true;
        else if(e.time>this->time)return false;
        return (e.kind<this->kind);
    }
};

set<Dish> waitDish;
int N,M;
Dish ds[101];
map<string,int> ms;
int T[101];
int K[101];
int leftDish[101];
int finTimes[101];
bool need[100001];
vector<string> order[101];

int main(){
    bool fst=true;
    while(cin>>N>>M&&(N|M)){
        if(fst)fst=false;
        else cout<<endl;
        waitDish.clear();
        ms.clear();
        for(int i=0;i<N;i++){
            cin>>ds[i].name>>ds[i].limit>>ds[i].time;
            ms[ds[i].name]=i;
            ds[i].idx=i;
        }
        for(int i=0;i<M;i++){
            order[i].clear();
            cin>>T[i];
            cin>>K[i];
            leftDish[i]=K[i];
            for(int j=0;j<K[i];j++){
                string str;
                cin>>str;
                order[i].push_back(str);
            }
        }
        priority_queue<Event> pq;
        bool isCook=false;
        for(int i=0;i<M;i++){
            Event e;
            e.kind=0;
            e.idx=i;
            e.time=T[i];
            pq.push(e);
        }
        while(pq.size()){
            Event e=pq.top();pq.pop();
            if(e.kind==0){
                for(int j=0;j<K[e.idx];j++){
                    int dk=ms[order[e.idx][j]];
                    Dish tmp=ds[dk];
                    tmp.whois=e.idx;
                    tmp.orderTime=e.time;
                    tmp.ordNum=j;
                    waitDish.insert(tmp);
                }
                Event ne;
                ne.time=e.time;
                ne.kind=2;
                pq.push(ne);
            }
            else if(e.kind==1){
                int dkind=e.idx;
                for(int i=0;i<e.who.size();i++){
                    int user=e.who[i];
                    leftDish[user]--;
                    if(leftDish[user]==0){
                        finTimes[user]=e.time;
                    }
                }
                isCook=false;
                Event ne;
                ne.time=e.time;
                ne.kind=2;
                pq.push(ne);
            }
            else{
                if(isCook||waitDish.size()==0)continue;
                isCook=true;
                Dish d=*(waitDish.begin());
                int lim=(waitDish.begin())->limit;
                Event ne;ne.kind=1;ne.idx=d.idx;
                ne.time=e.time+(waitDish.begin())->time;
                vector<Dish> tmp;
                for(set<Dish>::iterator it=waitDish.begin();it!=waitDish.end();it++){
                    tmp.push_back(*it);
                }
                vector<int> idxs;
                for(int i=0;i<tmp.size();i++){
                    if(lim>0&&tmp[i].idx==d.idx){
                        ne.who.push_back(tmp[i].whois);
                        lim--;
                    }
                    else idxs.push_back(i);
                }
                waitDish.clear();
                for(int i=0;i<idxs.size();i++){
                    int cur=idxs[i];
                    waitDish.insert(tmp[cur]);
                }
                pq.push(ne);
            }
        }
         for(int i=0;i<M;i++)
            cout<<finTimes[i]<<endl;
    }
    return 0;
}
accuracy: 1
time_ms: 280
memory_kb: 1052
final_rank: 13

code_snippet: #include <iostream>
#include <vector>
#include <queue>
#include <map>
#include <set>
#include <algorithm>
#include <string>

using namespace std;

/*
客がくる順番に注文を処理
客の注文は、もっとも時間がかかる料理から処理
おなじ時間の場合は、料理のindexが小さい方を先に処理
また、ある料理を調理開始する際,
キューに同じ料理があれば、同時に料理する
ただし同時に料理可能な量は限られる
*/
struct Dish{
    string name;
    int time;
    int limit;
    int orderTime;
    // 料理のidx
    int idx;
    // 注文した客のidx
    int whois;
    int ordNum;
    // かかる時間が長い順番でソート
    // 同じならidxで小さい順番にソート
    bool operator<(const Dish&dh)const{
        if(dh.orderTime>this->orderTime)return true;
        else if(dh.orderTime<this->orderTime)return false;
        else if(dh.time<this->time)return true;
        else if(dh.time>this->time)return false;
        else if(dh.idx>this->idx)return true;
        else if(dh.idx<this->idx)return false;
        // さらに同じなら、注文した客のidx順で取る
        else if(dh.whois>this->whois)return true;
        else if(dh.whois<this->whois)return false;
        return dh.ordNum<this->ordNum;
    }
};

/*
{客が到着,
料理終了,
料理開始}
のイベントを登録
優先順位はこの順番で
*/
struct Event{
    int time;
    // 料理の種類
    int idx;
    // kind=0 -> 客が到着,kind=1 -> 料理終了
    // kind=2 -> 料理開始
    int kind;
    // どの客の料理か
    vector<int> who;
    // 時間の小さい方を優先
    // 同じならば,優先順位が高いeventを優先
    bool operator<(const Event&e)const{
        if(e.time<this->time)return true;
        else if(e.time>this->time)return false;
        return (e.kind<this->kind);
    }
};

// 料理は客の頼んだ順番に関係なく
// 今登録されている料理の情報に依存して決定される
set<Dish> waitDish;
int N,M;
Dish ds[101];
map<string,int> ms;
int T[101];
int K[101];
int leftDish[101];
int finTimes[101];
bool need[100001];
vector<string> order[101];

int main(){
    bool fst=true;
    while(cin>>N>>M&&(N|M)){
        if(fst)fst=false;
        else cout<<endl;
        waitDish.clear();
        ms.clear();
        for(int i=0;i<N;i++){
            cin>>ds[i].name>>ds[i].limit>>ds[i].time;
            ms[ds[i].name]=i;
            ds[i].idx=i;
        }
        for(int i=0;i<M;i++){
            order[i].clear();
            cin>>T[i];
            cin>>K[i];
            // 残りの料理量
            leftDish[i]=K[i];
            for(int j=0;j<K[i];j++){
                string str;
                cin>>str;
                order[i].push_back(str);
            }
        }
        // 料理終了時か,客到着時に料理を開始
        priority_queue<Event> pq;
        bool isCook=false;
        // 客到着イベント登録
        for(int i=0;i<M;i++){
            Event e;
            e.kind=0;
            e.idx=i;
            e.time=T[i];
            pq.push(e);
        }
        while(pq.size()){
            Event e=pq.top();pq.pop();
            // 客到着
            if(e.kind==0){
                // 料理を登録
                for(int j=0;j<K[e.idx];j++){
                    int dk=ms[order[e.idx][j]];
                    Dish tmp=ds[dk];
                    tmp.whois=e.idx;
                    tmp.orderTime=e.time;
                    tmp.ordNum=j;
                    waitDish.insert(tmp);
                }
                // 料理開始イベントを登録
                Event ne;
                ne.time=e.time;
                ne.kind=2;
                pq.push(ne);
            }
            // 料理終了
            else if(e.kind==1){
                // 料理の種類
                int dkind=e.idx;
                // 登録してある料理を終了させる
                for(int i=0;i<e.who.size();i++){
                    // ユーザのid
                    int user=e.who[i];
                    leftDish[user]--;
                    // 注文終了時間を登録
                    if(leftDish[user]==0){
                        finTimes[user]=e.time;
                    }
                }
                isCook=false;
                // 料理開始イベントを登録
                Event ne;
                ne.time=e.time;
                ne.kind=2;
                pq.push(ne);
            }
            // 料理開始
            else{
                // すでに料理を開始している
                // または待ち料理が存在しない
                if(isCook||waitDish.size()==0)continue;
                isCook=true;
                Dish d=*(waitDish.begin());
                int lim=(waitDish.begin())->limit;
                Event ne;ne.kind=1;ne.idx=d.idx;
                ne.time=e.time+(waitDish.begin())->time;
                vector<Dish> tmp;
                for(set<Dish>::iterator it=waitDish.begin();it!=waitDish.end();it++){
                    tmp.push_back(*it);
                }
                vector<int> idxs;
                for(int i=0;i<tmp.size();i++){
                    if(lim>0&&tmp[i].idx==d.idx){
                        ne.who.push_back(tmp[i].whois);
                        lim--;
                    }
                    else idxs.push_back(i);
                }
                waitDish.clear();
                for(int i=0;i<idxs.size();i++){
                    int cur=idxs[i];
                    waitDish.insert(tmp[cur]);
                }
                //// limが0になるまで
                //ne.who.push_back(waitDish.begin()->whois);
                //lim--;
                //waitDish.erase(waitDish.begin());
                //for(set<Dish>::iterator it=waitDish.begin();it!=waitDish.end();it++){
                //    if(lim==0)break;
                //    // 同じ料理ならば、登録
                //    if(it->idx==d.idx){
                //        ne.who.push_back(it->whois);
                //        lim--;
                //        waitDish.erase(it);
                //        it=waitDish.begin();
                //    }
                //}
                //// イベントを登録
                pq.push(ne);
            }
        }
        // 終了時間を表示
        for(int i=0;i<M;i++)
            cout<<finTimes[i]<<endl;
    }
    return 0;
}
accuracy: 1
time_ms: 280
memory_kb: 1052
final_rank: 13

code_snippet: #include <iostream>
#include <iomanip>
#include <sstream>
#include <cstdio>
#include <string>
#include <vector>
#include <algorithm>
#include <complex>
#include <cstring>
#include <cstdlib>
#include <cmath>
#include <cassert>
#include <climits>
#include <queue>
#include <set>
#include <map>
#include <valarray>
#include <bitset>
#include <stack>
using namespace std;

#define REP(i,n) for(int i=0;i<(int)n;++i)
#define FOR(i,c) for(__typeof((c).begin())i=(c).begin();i!=(c).end();++i)
#define ALL(c) (c).begin(), (c).end()
typedef long long ll;
typedef pair<int,int> pii;
const int INF = 1<<29;
const double PI = acos(-1);
const double EPS = 1e-8;

struct Menu {
  int limit, time;
  int id;
  Menu(int limit, int time, int id) : limit(limit), time(time), id(id) {}
  Menu() {}
};
bool operator<(const Menu &a, const Menu &b) {
  return a.time != b.time ? a.time > b.time : a.id < b.id;
};

struct Order {
  int T;
  Menu menu;
  int id;
  Order(int T, Menu menu, int id) : T(T), menu(menu), id(id) {}
  Order() {}
};
bool operator<(const Order &a, const Order &b) {
  return a.T != b.T ? a.T < b.T : a.menu < b.menu;
}

Menu menu[20];
Order order[1000];
int ok[1000];                   // »Ì¶ðoµIíÁ½Ô
int K[100];
int endTime[100][10];

int main() {
  int n, m;
  int hoge = 0;
  while(cin >> n >> m, n || m) {
    if (hoge++) cout << endl;
    map<string, int> mp;
    REP(i, n) {
      string name;
      cin >> name >> menu[i].limit >> menu[i].time;
      menu[i].id = i;
      mp[name] = i;
    }
    int endnum[m];
    int num = 0;
    REP(i, m) {
      int T;
      cin >> T;
      cin >> K[i];
      REP(j, K[i]) {
        string dish;
        cin >> dish;
        order[num] = Order(T, menu[mp[dish]], i);
        num++;
      }
    }
    sort(order, order+num);
    ll nowtime = 0;
    memset(ok, -1, sizeof(ok));
    REP(i, num) {
      if (ok[i] >= 0) continue;
      nowtime = max(nowtime, (ll)order[i].T);
      //cout << i << " " << nowtime << " " << order[i].id << " " << order[i].menu.time << " " << order[i].menu.id << endl;
      ok[i] = nowtime + order[i].menu.time;
      int cnt = 1;
      for (int j=i+1; j<num && order[j].T<=nowtime && cnt<order[i].menu.limit; ++j) {
        if (order[j].menu.id == order[i].menu.id) {
          //cout << j << endl;
          ok[j] = nowtime + order[i].menu.time;
          cnt++;
        }
      }
      nowtime += order[i].menu.time;
    }
    int ans[m];
    memset(ans, 0, sizeof(ans));
    REP(i, num) {
      ans[order[i].id] = max(ans[order[i].id], ok[i]);
    }
    REP(i, m)
      cout << ans[i] << endl;
  }
}
accuracy: 1
time_ms: 40
memory_kb: 964
final_rank: 2

code_snippet: #include<iostream>
#include<algorithm>
#include<vector>
#include<map>
using namespace std;
#define REP(i,b,n) for(int i=b;i<n;i++)
#define rep(i,n)   REP(i,0,n)
#define pb         push_back

typedef long long ll;
class state{
public:
  int time,num;
  int cap;
  string name;
  bool operator<(const state&  a)const{
    if (time != a.time)return time >a.time;
    return num < a.num;
  }
};

vector<ll> solve(vector<state> &dish,
		 vector<int> &come,vector<vector<int> >&ord){
  ll now = 0;
  int p=0;
  vector<ll> ret(come.size(),(1LL)<<50);
  while(p < come.size()){
    if (come[p] > now)now=come[p];

    int cap=-1,num=-1;
    rep(i,dish.size()){
      if(ord[p][i] != 0){
	num=i;
	cap=dish[i].cap;
	break;
      }
    }

    REP(i,p,ord.size() && cap){
      if (now < come[i])break;
      if (cap >= ord[i][num]){
	cap-=ord[i][num];
	ord[i][num]=0;
      }else if (cap < ord[i][num]){
	ord[i][num]-=cap;
	cap=0;
      }
    }

    now=now+dish[num].time;
    rep(i,ord.size()){
      bool isok=true;
      rep(j,ord[i].size())if (ord[i][j]!=0)isok=false;
      if (isok)ret[i]=min(ret[i],now);
      if (p == i && isok)p++;
    }
  }
  return ret;
}

int getindex(string a,map<string,int> &M){
  int index = M.size();
  if (M.count(a)==0)M[a]=index;
  return M[a];
}

main(){
  int n,m;
  int te=0;
  while(cin>>n>>m && n){
    if( te++)cout << endl;
    vector<state> in(n);
    vector<int> come(m);
    vector<vector<int> > ord(m);
    map<string,int> M;
    
    rep(i,n){
      cin>>in[i].name>>in[i].cap>>in[i].time;
      in[i].num=i;
    }


    sort(in.begin(),in.end());
    rep(i,n)getindex(in[i].name,M);

    rep(i,m){
      cin>>come[i];
      rep(j,n)ord[i].pb(0);
      int k;
      cin>>k;
      rep(j,k){
	string tmp;cin>>tmp;ord[i][getindex(tmp,M)]++;
      }
    }

    vector<ll> ans=solve(in,come,ord);
    rep(i,ans.size())cout << ans[i]<<endl;
  }
  return false;
}
accuracy: 1
time_ms: 80
memory_kb: 956
final_rank: 4

code_snippet: #include <iostream>
#include <string>
#include <map>
#include <queue>
#include <algorithm>
using namespace std;

enum EVENT{ORDER, COOKED};

class Event
{
public:
	int c,t,s,id;
	EVENT e;
	
	Event(int c, int t, int s, int id, EVENT e)
	:c(c),t(t),e(e),s(s),id(id)
	{}
	
	bool operator<(const Event& a) const
	{
		if(t!=a.t) return t>a.t;
		if(e!=a.e) return e<a.e;
		if(c==a.c) return s>a.s;
		return c>a.c;
	}
};

class Order
{
public:
	int id,pt;
	Order(int id, int pt)
	:id(id),pt(pt)
	{}
	
	bool operator<(const Order& a) const
	{
		if(pt!=a.pt) return pt>a.pt;
		return id<a.id;
	}
};

int main()
{
	bool f=true;
	int M,N;
	while(cin >> M >> N, (M||N))
	{
		if(!f) cout << endl;
		f=false;
		
		int limit[20], time[20];
		map<string, int> d;
		for(int i=0; i<M; i++)
		{
			int l,t;
			string n;
			cin >> n >> l >> t;
			d[n]=i;
			
			limit[i]=l; time[i]=t;
		}
		
		priority_queue<Event> q;
		
		int order[100],cooked[100]={0},cookid=-1,cooking=0,cooktime=-1,served[100],pretime=-1;
		for(int i=0; i<N; i++)
		{
			int t,o;
			cin >> t >> o;
			order[i]=o;
			vector<Order> seq;
			for(int j=0; j<o; j++)
			{
				string n;
				cin >> n;
				seq.push_back(Order(d[n], time[d[n]]));
			}
			sort(seq.begin(), seq.end());
			for(int j=0; j<seq.size(); j++)
			{
				q.push(Event(i,t,j,seq[j].id,ORDER));
			}
		}
		while(!q.empty())
		{
			Event e=q.top(); q.pop();
			if(e.e==ORDER)
			{
				if(cookid==e.id&&cooking<limit[e.id]&&pretime==e.t||cooking==0)
				{
					int tm=e.t+time[e.id];
					pretime=e.t;
					cooktime=tm;
					cooking++;
					cookid=e.id;
					q.push(Event(e.c, tm,e.s, e.id,COOKED));
				}
				else
				{
					q.push(Event(e.c, cooktime,e.s, e.id,e.e));
					continue;
				}
			}
			else
			{
				cooking--;
				cooked[e.c]++;
				if(cooked[e.c]==order[e.c])
					served[e.c]=e.t;
			}
		}
		
		for(int i=0; i<N; i++)
			cout << served[i] << endl;
	}
}
accuracy: 1
time_ms: 160
memory_kb: 976
final_rank: 9