Problem:
Problem F
Deadlock Detection
You are working on an analysis of a system with multiple processes and some kinds of resource (such as memory pages, DMA channels, and I/O ports). Each kind of resource has a certain number of instances. A process has to acquire resource instances for its execution. The number of required instances of a resource kind depends on a process. A process finishes its execution and terminates eventually after all the resource in need are acquired. These resource instances are released then so that other processes can use them. No process releases instances before its termination. Processes keep trying to acquire resource instances in need, one by one, without taking account of behavior of other processes. Since processes run independently of others, they may sometimes become unable to finish their execution because of
deadlock
.
A process has to wait when no more resource instances in need are available until some other processes release ones on their termination. Deadlock is a situation in which two or more processes wait for termination of each other, and, regrettably, forever. This happens with the following scenario: One process A acquires the sole instance of resource X, and another process B acquires the sole instance of another resource Y; after that, A tries to acquire an instance of Y, and B tries to acquire an instance of X. As there are no instances of Y other than one acquired by B, A will never acquire Y before B finishes its execution, while B will never acquire X before A finishes. There may be more complicated deadlock situations involving three or more processes.
Your task is, receiving the system's resource allocation time log (from the system's start to a certain time), to determine when the system fell into a
deadlock-unavoidable
state. Deadlock may usually be avoided by an appropriate allocation order, but deadlock-unavoidable states are those in which some resource allocation has already been made and no allocation order from then on can ever avoid deadlock.
Let us consider an example corresponding to Sample Input 1 below. The system has two kinds of resource $R_1$ and $R_2$, and two processes $P_1$ and $P_2$. The system has three instances of $R_1$ and four instances of $R_2$. Process $P_1$ needs three instances of $R_1$ and two instances of $R_2$ to finish its execution, while process $P_2$ needs a single instance of $R_1$ and three instances of $R_2$. The resource allocation time log is given as follows.
At time 4, $P_2$ acquired $R_1$ and the number of available instances of $R_1$ became less than $P_1$'s need of $R_1$. Therefore, it became necessary for $P_1$ to wait $P_2$ to terminate and release the instance. However, at time 5, $P_1$ acquired $R_2$ necessary for $P_2$ to finish its execution, and thus it became necessary also for $P_2$ to wait $P_1$; the deadlock became unavoidable at this time.
Note that the deadlock was still avoidable at time 4 by finishing $P_2$ first (Sample Input 2).
Input
...(truncated)

Submitted solutions:

code_snippet: #include <iostream>
#include <algorithm>
#include <cstring>
#include <cstdio>
#include <map>
#include <set>
#include <bitset>
#include <string>
#include <queue>
#include <cmath>
#include <vector>
#define CLR0(a) (memset(a, 0, sizeof(a)))
#define CLR1(a) (memset(a, -1, sizeof(a)))
#define CLRf(a) (memset(a, 0x3f, sizeof(a)))
typedef long long ll;
typedef unsigned long long ull;
using namespace std;

int p, r, t;
vector<int> sr[310];
vector<int> pr[310][310];
int remain[310][310];
bool ok(int mid)
{
	for (int i = 1; i <= r; i++)
		remain[0][i] = sr[i][0] - (upper_bound(++sr[i].begin(), sr[i].end(), mid) - sr[i].begin()) + 1;
	for (int i = 1; i <= p; i++)
		for (int j = 1; j <= r; j++)
			remain[i][j] = pr[i][j][0] - (upper_bound(++pr[i][j].begin(), pr[i][j].end(), mid) - pr[i][j].begin()) + 1;

	for (int i = 1; i <= p; i++)
	{
		int f = 0;
		for (int j = 1; j <= r; j++)
			if (remain[i][j] != 0)
				f = 1;
		if (f == 0)
		{
			remain[i][1] = -1;
			for (int j = 1; j <= r; j++)
				remain[0][j] += pr[i][j][0];
		}
	}

	for (int i = 1; ; i++)
	{
		int flag = 0;
		for (int j = 1; j <= p; j++)
		{
			if (remain[j][1] == -1)continue;
			int f = 0;
			for (int k = 1; k <= r;k++)
				if (remain[0][k] < remain[j][k])
				{
					f = 1;
					break;
				}
			if (f == 0)
			{
				for (int k = 1; k <= r; k++)
					remain[0][k] += pr[j][k][0] - remain[j][k];
				remain[j][1] = -1;
				flag = 1;
			}
		}
		if (flag == 0)break;
	}
	for (int i = 1; i <= p; i++)
		if (remain[i][1] != -1)return 0;
	return 1;
}
int main()
{
	//freopen("C:\\Users\\falser\\Desktop\\data\\F\\005.in", "r", stdin);
	scanf("%d%d%d", &p, &r, &t);
	for (int i = 1, x; i <= r; i++)
	{
		scanf("%d", &x);
		sr[i].push_back(x);
	}
	for (int i = 1, x; i <= p; i++)
		for (int j = 1; j <= r; j++)
		{
			scanf("%d", &x);
			pr[i][j].push_back(x);
		}
	for (int i = 1, ip, ir; i <= t; i++)
	{
		scanf("%d%d", &ip, &ir);
		sr[ir].push_back(i);
		pr[ip][ir].push_back(i);
	}
	for (int i = 1; i <= r; i++)sr[i].push_back(t + 1);
	for (int i = 1; i <= p; i++)
		for (int j = 1; j <= r; j++)
			pr[i][j].push_back(t + 1);
	if (ok(t))
	{
		printf("-1\n");
		return 0;
	}
	//int l = 1, ri = t, mid;
	//while (ri - l >= 10)
	//{
	//	mid = (l + ri) / 2;
	//	if (ok(mid))l = mid;
	//	else ri = mid - 1;
	//}
	//for (int i = l; i <= ri + 1; i++)
	//	if (!ok(i))
	//	{
	//		printf("%d\n", i);
	//		break;
	//	}
	int ll = 1, rr = t;
	int ans;
	while (ll <=rr)
	{
		int mid = (ll + rr) >> 1;
		if (ok(mid)==0)ans=mid,rr=mid-1;
		else ll = mid + 1;
	}
	printf("%d\n", ans);
	return 0;
}
accuracy: 1
time_ms: 30
memory_kb: 11228
final_rank: 6

code_snippet: #include <bits/stdc++.h>
using namespace std;

bool check_deadlock(int Process, int Resources, vector<int> reso, vector<vector<int>> need, vector<vector<int>> initial_need) {
    vector<bool> Used(Process, false);
    int remain = Process;
    for (int i = 0; i < Process; i++) {
        int total = 0;
        for (int j = 0; j < Resources; j++) total += need[i][j];
        if (total == 0) { remain--; Used[i] = true; }
    }

    // Simulation
    for (int loops = 0; loops < remain; loops++) {
        bool success = false;
        for (int i = 0; i < Process; i++) {
            if (Used[i] == true) continue;
            bool flag = false;
            for (int j = 0; j < Resources; j++) {
                if (reso[j] < need[i][j]) { flag = true; break; }
            }
            if (flag == true) continue;
            success = true;
            Used[i] = true;
            for (int j = 0; j < Resources; j++) {
                reso[j] += initial_need[i][j] - need[i][j];
                need[i][j] = 0;
            }
            break;
        }
        if (success == false) return false;
    }

    // Challenge Succeeded
    return true;
}

int main() {
    // Step 1. Input
    int Process, Resources, Time; cin >> Process >> Resources >> Time;
    vector<int> reso(Resources, 0);
    vector<vector<int>> initial_need(Process, vector<int>(Resources, 0));
    vector<int> log_p(Time, 0);
    vector<int> log_r(Time, 0);
    for (int i = 0; i < Resources; i++) cin >> reso[i];
    for (int i = 0; i < Process; i++) {
        for (int j = 0; j < Resources; j++) cin >> initial_need[i][j];
    }
    for (int i = 0; i < Time; i++) cin >> log_p[i] >> log_r[i];
    for (int i = 0; i < Time; i++) log_p[i] -= 1;
    for (int i = 0; i < Time; i++) log_r[i] -= 1;

    // Step 2. Solve
    int cl = 0, cr = Time, cm, minx = (1 << 30);
    for (int i = 0; i < 20; i++) {
        cm = (cl + cr) / 2;
        vector<vector<int>> new_need = initial_need;
        vector<int> new_reso = reso;

        // Initial Simulation
        for (int j = 0; j <= cm; j++) {
            new_reso[log_r[j]] -= 1;
            new_need[log_p[j]][log_r[j]] -= 1;
        }
        for (int j = 0; j < Process; j++) {
            int total_count = 0;
            for (int k = 0; k < Resources; k++) {
                total_count += new_need[j][k];
            }
            if (total_count == 0) {
                for (int k = 0; k < Resources; k++) new_reso[k] += initial_need[j][k];
            }
        }

        // Check
        bool success = check_deadlock(Process, Resources, new_reso, new_need, initial_need);
        if (success == true) { cl = cm; }
        else { cr = cm; minx = min(minx, cm); }
    }

    // Output
    cout << (minx == (1 << 30) ? -1 : minx + 1) << endl;
    return 0;
}
accuracy: 1
time_ms: 60
memory_kb: 5988
final_rank: 5

code_snippet: #include <bits/stdc++.h>
using namespace std;

bool check_deadlock(int Process, int Resources, vector<int> reso, vector<vector<int>> need, vector<vector<int>> initial_need) {
    vector<bool> Used(Process, false);

    // Simulation
    for (int loops = 0; loops < Process; loops++) {
        bool success = false;
        for (int i = 0; i < Process; i++) {
            if (Used[i] == true) continue;
            bool flag = false;
            for (int j = 0; j < Resources; j++) {
                if (reso[j] < need[i][j]) { flag = true; break; }
            }
            if (flag == true) continue;
            success = true;
            Used[i] = true;
            for (int j = 0; j < Resources; j++) {
                reso[j] += initial_need[i][j] - need[i][j];
                need[i][j] = 0;
            }
            break;
        }
        if (success == false) return false;
    }

    // Challenge Succeeded
    return true;
}

int main() {
    // Step 1. Input
    int Process, Resources, Time; cin >> Process >> Resources >> Time;
    vector<int> reso(Resources, 0);
    vector<vector<int>> initial_need(Process, vector<int>(Resources, 0));
    vector<int> log_p(Time, 0);
    vector<int> log_r(Time, 0);
    for (int i = 0; i < Resources; i++) cin >> reso[i];
    for (int i = 0; i < Process; i++) {
        for (int j = 0; j < Resources; j++) cin >> initial_need[i][j];
    }
    for (int i = 0; i < Time; i++) cin >> log_p[i] >> log_r[i];
    for (int i = 0; i < Time; i++) log_p[i] -= 1;
    for (int i = 0; i < Time; i++) log_r[i] -= 1;

    // Step 2. Solve
    int cl = 0, cr = Time, cm, minx = (1 << 30);
    for (int i = 0; i < 20; i++) {
        cm = (cl + cr) / 2;
        vector<vector<int>> new_need = initial_need;
        vector<int> new_reso = reso;

        // Initial Simulation
        for (int j = 0; j <= cm; j++) {
            new_reso[log_r[j]] -= 1;
            new_need[log_p[j]][log_r[j]] -= 1;
        }
        for (int j = 0; j < Process; j++) {
            int total_count = 0;
            for (int k = 0; k < Resources; k++) {
                total_count += new_need[j][k];
            }
            if (total_count == 0) {
                for (int k = 0; k < Resources; k++) new_reso[k] += initial_need[j][k];
            }
        }

        // Check
        bool success = check_deadlock(Process, Resources, new_reso, new_need, initial_need);
        if (success == true) { cl = cm; }
        else { cr = cm; minx = min(minx, cm); }
    }

    // Output
    cout << (minx == (1 << 30) ? -1 : minx + 1) << endl;
    return 0;
}
accuracy: 0.03571428571428571
time_ms: 20
memory_kb: 4028
final_rank: 15

code_snippet: #include<bits/stdc++.h>
using namespace std;
using ll=long long;

int main(){
	int p, r, t;
	cin >> p >> r >> t;
	vector<int> l(r);
	for(int i = 0; i < r; ++i) cin >> l[i];
	vector<vector<int>> N(p, vector<int>(r));
	for(int i = 0; i < p; ++i) for(int j = 0; j < r; ++j) cin >> N[i][j];
	vector<int> P(t), R(t);
	for(int i = 0; i < t; ++i) {
		cin >> P[i] >> R[i];
		--P[i];
		--R[i];
	}

	int left = -1, right = t+1;
	while(right-left>1){
		int mid = (left+right)>>1;

		auto tn = N;
		auto tl = l;

		vector<int> flag(p);

		for(int i = 0; i < p; ++i){
			for(int j = 0; j < r; ++j){
				if(tn[i][j] == 0) ++flag[i];
			}
		}

		for(int i = 0; i < mid; ++i){
			--tl[R[i]];
			--tn[P[i]][R[i]];
			if(tn[P[i]][R[i]] == 0){
				++flag[P[i]];
				if(flag[P[i]] == r){
					for(int j = 0; j < r; ++j){
						tl[j] += N[P[i]][j];
					}
				}
			}
		}

		for(int i = 0; i < p; ++i){
			bool flag2 = false;
			for(int j = 0; j < p; ++j){
				if(flag[j] == r) continue;
				bool al = true;
				for(int k = 0; k < r; ++k){
					if(tl[k] >= tn[j][k]){
						al = true;
					}else{
						al = false;
						break;
					}
				}
				if(al){
					flag2 = true;
					flag[j] = r;
					for(int k = 0; k < r; ++k){
						tl[k] += N[j][k]-tn[j][k];
					}
				}
			}
			if(!flag2) break;
		}

		if(ranges::count(flag, r) == p){
			left = mid;
		}else{
			right = mid;
		}
	}

	if(right == t+1){
		cout << -1 << endl;
	}else{
		cout << right << endl;
	}
	return 0;
}
accuracy: 1
time_ms: 40
memory_kb: 5632
final_rank: 4

code_snippet: #include<bits/stdc++.h>
using namespace std;
using ll=long long;

int main(){
	int p, r, t;
	cin >> p >> r >> t;
	vector<int> l(r);
	for(int i = 0; i < r; ++i) cin >> l[i];
	vector<vector<int>> N(p, vector<int>(r));
	for(int i = 0; i < p; ++i) for(int j = 0; j < r; ++j) cin >> N[i][j];
	vector<int> P(t), R(t);
	for(int i = 0; i < t; ++i) {
		cin >> P[i] >> R[i];
		--P[i];
		--R[i];
	}

	int left = -1, right = t+1;
	while(right-left>1){
		int mid = (left+right)>>1;

		auto tn = N;
		auto tl = l;

		vector<int> flag(p);

		for(int i = 0; i < p; ++i){
			for(int j = 0; j < r; ++j){
				if(tn[i][j] == 0) ++flag[i];
			}
		}

		for(int i = 0; i < mid; ++i){
			--tl[R[i]];
			--tn[P[i]][R[i]];
			if(tn[P[i]][R[i]] == 0){
				++flag[P[i]];
				if(flag[P[i]] == r){
					for(int j = 0; j < r; ++j){
						tl[j] += N[P[i]][j];
					}
				}
			}
		}

		for(int i = 0; i < p; ++i){
			bool flag2 = false;
			for(int j = 0; j < p; ++j){
				bool al = true;
				for(int k = 0; k < r; ++k){
					if(tl[k] >= tn[j][k]){
						al = true;
					}else{
						al = false;
						break;
					}
				}
				if(al){
					flag2 = true;
					flag[j] = r;
					for(int k = 0; k < r; ++k){
						tl[k] += N[j][k]-tn[j][k];
					}
				}
			}
			if(!flag2) break;
		}

		if(ranges::count(flag, r) == p){
			left = mid;
		}else{
			right = mid;
		}
	}

	if(right == t+1){
		cout << -1 << endl;
	}else{
		cout << right << endl;
	}
	return 0;
}
accuracy: 0.03571428571428571
time_ms: 30
memory_kb: 4224
final_rank: 19

code_snippet: #include <bits/stdc++.h>

using namespace std;

#define rep(i, a, b) for (ll i = (ll)(a); i < (ll)(b); i++)
#define rrep(i, a, b) for (ll i = (ll)(b)-1; i >= (ll)(a); i--)
#define ALL(v) (v).begin(), (v).end()
#define UNIQUE(v) sort(ALL(v)), (v).erase(unique(ALL(v)), (v).end())
#define SZ(v) (int)v.size()
#define MIN(v) *min_element(ALL(v))
#define MAX(v) *max_element(ALL(v))
#define LB(v, x) int(lower_bound(ALL(v), (x)) - (v).begin())
#define UB(v, x) int(upper_bound(ALL(v), (x)) - (v).begin())

using uint = unsigned int;
using ll = long long int;
using ull = unsigned long long;
using i128 = __int128_t;
using u128 = __uint128_t;
const int inf = 0x3fffffff;
const ll INF = 0x1fffffffffffffff;

template <typename T> inline bool chmax(T &a, T b) {
    if (a < b) {
        a = b;
        return 1;
    }
    return 0;
}
template <typename T> inline bool chmin(T &a, T b) {
    if (a > b) {
        a = b;
        return 1;
    }
    return 0;
}
template <typename T, typename U> T ceil(T x, U y) {
    assert(y != 0);
    if (y < 0)
        x = -x, y = -y;
    return (x > 0 ? (x + y - 1) / y : x / y);
}
template <typename T, typename U> T floor(T x, U y) {
    assert(y != 0);
    if (y < 0)
        x = -x, y = -y;
    return (x > 0 ? x / y : (x - y + 1) / y);
}
template <typename T> int popcnt(T x) {
    return __builtin_popcountll(x);
}
template <typename T> int topbit(T x) {
    return (x == 0 ? -1 : 63 - __builtin_clzll(x));
}
template <typename T> int lowbit(T x) {
    return (x == 0 ? -1 : __builtin_ctzll(x));
}

template <class T, class U>
ostream &operator<<(ostream &os, const pair<T, U> &p) {
    os << "P(" << p.first << ", " << p.second << ")";
    return os;
}
template <typename T> ostream &operator<<(ostream &os, const vector<T> &vec) {
    os << "{";
    for (int i = 0; i < vec.size(); i++) {
        os << vec[i] << (i + 1 == vec.size() ? "" : ", ");
    }
    os << "}";
    return os;
}
template <typename T, typename U>
ostream &operator<<(ostream &os, const map<T, U> &map_var) {
    os << "{";
    for (auto itr = map_var.begin(); itr != map_var.end(); itr++) {
        os << "(" << itr->first << ", " << itr->second << ")";
        itr++;
        if (itr != map_var.end())
            os << ", ";
        itr--;
    }
    os << "}";
    return os;
}
template <typename T> ostream &operator<<(ostream &os, const set<T> &set_var) {
    os << "{";
    for (auto itr = set_var.begin(); itr != set_var.end(); itr++) {
        os << *itr;
        ++itr;
        if (itr != set_var.end())
            os << ", ";
        itr--;
    }
    os << "}";
    return os;
}
#ifdef LOCAL
#define show(...) _show(0, #__VA_ARGS__, __VA_ARGS__)
#else
#define show(...) true
#endif
template <typename T> void _show(int i, T name) {
    cerr << '\n';
}
template <typename T1, typename T2, typename... T3>
void _show(int i, const T1 &a, const T2 &b, const T3 &...c) {
    for (; a[i] != ',' && a[i] != '\0'; i++)
        cerr << a[i];
    cerr << ":" << b << " ";
    _show(i + 1, a, c...);
}

/**
 * @brief template
 */

int main() {
    int N, M, K;
    cin >> N >> M >> K;
    vector<int> L(M);
    vector<vector<int>> A(N,vector<int>(M));
    vector<int> P(K), R(K);
    rep(i,0,M) cin >> L[i];
    rep(i,0,N) rep(j,0,M) cin >> A[i][j];
    rep(i,0,K) cin >> P[i] >> R[i], P[i]--, R[i]--;
    auto Judge = [&](int X) -> bool {
        vector<int> CurL = L;
        vector<vector<int>> Use(N,vector<int>(M,0));
        rep(i,0,X) {
            CurL[R[i]]--;
            Use[P[i]][R[i]]++;
        }
        vector<vector<int>> ord(M,vector<int>(N));
        rep(i,0,M) iota(ALL(ord[i]),0);
        rep(i,0,M) {
            sort(ALL(ord[i]),[&](int j, int k){return A[j][i]-Use[j][i]<A[k][i]-Use[k][i];});
        }
        vector<int> Pos(M,0), Count(N,0);
        queue<int> Q;
        rep(i,0,M) {
            while(Pos[i]<N) {
                int id = ord[i][Pos[i]];
                if (Use[id][i]+CurL[i] >= A[id][i] || Use[id][i] == A[id][i]) {
                    Count[id]++;
                    if (Count[id] == M) Q.push(id);
                    Pos[i]++;
                }
                else break;
            }
        }
        while(!Q.empty()) {
            int Now = Q.front();
            Q.pop();
            rep(i,0,M) {
                CurL[i] += Use[Now][i];
            }
            rep(i,0,M) {
                while(Pos[i]<N) {
                    int id = ord[i][Pos[i]];
                    if (Use[id][i]+CurL[i] >= A[id][i] || Use[id][i] == A[id][i]) {
                        Count[id]++;
                        if (Count[id] == M) Q.push(id);
                        Pos[i]++;
                    }
                    else break;
                }
            }
        }
        bool check = true;
        rep(i,0,N) if (Count[i] != M) check = false;
        return check;
    };
    int OK = 0, NG = K+1;
    while(NG - OK > 1) {
        int MID = (OK + NG) / 2;
        if (Judge(MID)) OK = MID;
        else NG = MID;
    }
    cout << (NG == K+1 ? -1 : NG) << endl;
}
accuracy: 1
time_ms: 120
memory_kb: 5728
final_rank: 7

code_snippet: #include <bits/stdc++.h>

using namespace std;

#define rep(i, a, b) for (ll i = (ll)(a); i < (ll)(b); i++)
#define rrep(i, a, b) for (ll i = (ll)(b)-1; i >= (ll)(a); i--)
#define ALL(v) (v).begin(), (v).end()
#define UNIQUE(v) sort(ALL(v)), (v).erase(unique(ALL(v)), (v).end())
#define SZ(v) (int)v.size()
#define MIN(v) *min_element(ALL(v))
#define MAX(v) *max_element(ALL(v))
#define LB(v, x) int(lower_bound(ALL(v), (x)) - (v).begin())
#define UB(v, x) int(upper_bound(ALL(v), (x)) - (v).begin())

using uint = unsigned int;
using ll = long long int;
using ull = unsigned long long;
using i128 = __int128_t;
using u128 = __uint128_t;
const int inf = 0x3fffffff;
const ll INF = 0x1fffffffffffffff;

template <typename T> inline bool chmax(T &a, T b) {
    if (a < b) {
        a = b;
        return 1;
    }
    return 0;
}
template <typename T> inline bool chmin(T &a, T b) {
    if (a > b) {
        a = b;
        return 1;
    }
    return 0;
}
template <typename T, typename U> T ceil(T x, U y) {
    assert(y != 0);
    if (y < 0)
        x = -x, y = -y;
    return (x > 0 ? (x + y - 1) / y : x / y);
}
template <typename T, typename U> T floor(T x, U y) {
    assert(y != 0);
    if (y < 0)
        x = -x, y = -y;
    return (x > 0 ? x / y : (x - y + 1) / y);
}
template <typename T> int popcnt(T x) {
    return __builtin_popcountll(x);
}
template <typename T> int topbit(T x) {
    return (x == 0 ? -1 : 63 - __builtin_clzll(x));
}
template <typename T> int lowbit(T x) {
    return (x == 0 ? -1 : __builtin_ctzll(x));
}

template <class T, class U>
ostream &operator<<(ostream &os, const pair<T, U> &p) {
    os << "P(" << p.first << ", " << p.second << ")";
    return os;
}
template <typename T> ostream &operator<<(ostream &os, const vector<T> &vec) {
    os << "{";
    for (int i = 0; i < vec.size(); i++) {
        os << vec[i] << (i + 1 == vec.size() ? "" : ", ");
    }
    os << "}";
    return os;
}
template <typename T, typename U>
ostream &operator<<(ostream &os, const map<T, U> &map_var) {
    os << "{";
    for (auto itr = map_var.begin(); itr != map_var.end(); itr++) {
        os << "(" << itr->first << ", " << itr->second << ")";
        itr++;
        if (itr != map_var.end())
            os << ", ";
        itr--;
    }
    os << "}";
    return os;
}
template <typename T> ostream &operator<<(ostream &os, const set<T> &set_var) {
    os << "{";
    for (auto itr = set_var.begin(); itr != set_var.end(); itr++) {
        os << *itr;
        ++itr;
        if (itr != set_var.end())
            os << ", ";
        itr--;
    }
    os << "}";
    return os;
}
#ifdef LOCAL
#define show(...) _show(0, #__VA_ARGS__, __VA_ARGS__)
#else
#define show(...) true
#endif
template <typename T> void _show(int i, T name) {
    cerr << '\n';
}
template <typename T1, typename T2, typename... T3>
void _show(int i, const T1 &a, const T2 &b, const T3 &...c) {
    for (; a[i] != ',' && a[i] != '\0'; i++)
        cerr << a[i];
    cerr << ":" << b << " ";
    _show(i + 1, a, c...);
}

/**
 * @brief template
 */

int main() {
    int N, M, K;
    cin >> N >> M >> K;
    vector<int> L(M);
    vector<vector<int>> A(N,vector<int>(M));
    vector<int> P(K), R(K);
    rep(i,0,M) cin >> L[i];
    rep(i,0,N) rep(j,0,M) cin >> A[i][j];
    rep(i,0,K) cin >> P[i] >> R[i], P[i]--, R[i]--;
    auto Judge = [&](int X) -> bool {
        vector<int> CurL = L;
        vector<vector<int>> Use(N,vector<int>(M,0));
        rep(i,0,X) {
            CurL[R[i]]--;
            Use[P[i]][R[i]]++;
        }
        vector<vector<int>> ord(M,vector<int>(N));
        rep(i,0,M) iota(ALL(ord[i]),0);
        rep(i,0,M) {
            sort(ALL(ord[i]),[&](int j, int k){return A[j][i]-Use[j][i]<A[k][i]-Use[k][i];});
        }
        vector<int> Pos(M,0), Count(N,0);
        queue<int> Q;
        rep(i,0,M) {
            while(Pos[i]<N) {
                int id = ord[i][Pos[i]];
                if (Use[id][i]+CurL[i] >= A[id][i]) {
                    Count[id]++;
                    if (Count[id] == M) Q.push(id);
                    Pos[i]++;
                }
                else break;
            }
        }
        while(!Q.empty()) {
            int Now = Q.front();
            Q.pop();
            rep(i,0,M) {
                CurL[i] += Use[Now][i];
            }
            rep(i,0,M) {
                while(Pos[i]<N) {
                    int id = ord[i][Pos[i]];
                    if (Use[id][i]+CurL[i] >= A[id][i]) {
                        Count[id]++;
                        if (Count[id] == M) Q.push(id);
                        Pos[i]++;
                    }
                    else break;
                }
            }
        }
        bool check = true;
        rep(i,0,N) if (Count[i] != M) check = false;
        return check;
    };
    int OK = 0, NG = K+1;
    while(NG - OK > 1) {
        int MID = (OK + NG) / 2;
        if (Judge(MID)) OK = MID;
        else NG = MID;
    }
    cout << (OK == K ? -1 : OK + 1) << endl;
}
accuracy: 0.03571428571428571
time_ms: 20
memory_kb: 3932
final_rank: 14

code_snippet: #include <bits/stdc++.h>
using namespace std;

#define rep(i, n) for (int i = 0; i < (n); i++)
#define per(i, n) for (int i = (n)-1; i >= 0; i--)
#define rep2(i, l, r) for (int i = (l); i < (r); i++)
#define per2(i, l, r) for (int i = (r)-1; i >= (l); i--)
#define each(e, x) for (auto &e : x)
#define sz(x) (int)x.size()
#define all(x) begin(x), end(x)
#define rall(x) rbegin(x), rend(x)
#define eb emplace_back
#define MM << ' ' <<
#define TT template <typename T>
using ll = long long;
using pii = pair<int, int>;
using pll = pair<ll, ll>;

TT bool chmin(T &x, T y) { return x > y ? (x = y, true) : false; }
TT bool chmax(T &x, T y) { return x < y ? (x = y, true) : false; }

TT using minheap = priority_queue<T, vector<T>, greater<T>>;
TT using maxheap = priority_queue<T>;

TT void print(vector<T> v, T x = 0) {
    int n = sz(v);
    rep(i, n) cout << v[i] + x << (i == n - 1 ? '\n' : ' ');
    if (n == 0) cout << '\n';
}

TT void printn(vector<T> v, T x = 0) {
    int n = sz(v);
    rep(i, n) cout << v[i] + x << '\n';
}

TT void rearrange(vector<T> &v) {
    sort(all(v));
    v.erase(unique(all(v)), end(v));
}

TT int lb(vector<T> &v, T x) { return lower_bound(all(v), x) - begin(v); }
TT int ub(vector<T> &v, T x) { return upper_bound(all(v), x) - begin(v); }

const int inf = (1 << 30) - 1;
const ll INF = (1LL << 60) - 1;

struct io_setup {
    io_setup() {
        ios_base::sync_with_stdio(false);
        cin.tie(NULL);
        cout << fixed << setprecision(15);
    }
} io_setup;

int main() {
    int n, m, q;
    cin >> n >> m >> q;
    vector<int> r(m);
    rep(i, m) cin >> r[i];
    vector<vector<int>> need(n, vector<int>(m, 0)), ac = need;
    rep(i, n) rep(j, m) cin >> need[i][j];
    vector<int> st(n, 0);
    vector<vector<int>> ls(n + 1);
    vector<vector<int>> rs(n + 1, r);
    rep(i, n) ls[0].eb(i);
    queue<pair<pii, int>> que;
    auto sub = [&](int i, int j, int d) {
        rs[i][j] -= d;
        assert(rs[i][j] >= 0);
        vector<int> nls;
        each(e, ls[i]) {
            if (rs[i][j] < need[e][j]) {
                rep(k, m) if (ac[e][k]) que.emplace(pair(i + 1, k), ac[e][k]);
                ls[i + 1].eb(e);
                st[e]++;
            }
            else
                nls.eb(e);
        }
        swap(ls[i], nls);
    };
    rep2(t, 1, q + 1) {
        int x, y;
        cin >> x >> y, x--, y--;
        need[x][y]--, ac[x][y]++;
        bool fin = true;
        rep(j, m) fin &= need[x][j] == 0;
        if (fin) {
            rep(i, st[x] + 1) {
                rep(j, m) rs[i][j] += ac[x][j];
                rs[i][y]--;
            }
        }
        else {
            rep(i, st[x] + 1) {
                que.emplace(pair(i, y), 1);
                while (sz(que)) {
                    auto [ij, d] = que.front();
                    auto [i, j] = ij;
                    que.pop();
                    sub(i, j, d);
                    if (sz(ls[i]) == 0 && sz(ls[i + 1]) > 0) {
                        cout << t << endl;
                        return 0;
                    }
                }
            }
        }        
    }
    cout << -1 << endl;
}
accuracy: 1
time_ms: 580
memory_kb: 4568
final_rank: 11

code_snippet: #include <bits/stdc++.h>
using namespace std;

#define rep(i, n) for (int i = 0; i < (n); i++)
#define per(i, n) for (int i = (n)-1; i >= 0; i--)
#define rep2(i, l, r) for (int i = (l); i < (r); i++)
#define per2(i, l, r) for (int i = (r)-1; i >= (l); i--)
#define each(e, x) for (auto &e : x)
#define sz(x) (int)x.size()
#define all(x) begin(x), end(x)
#define rall(x) rbegin(x), rend(x)
#define eb emplace_back
#define MM << ' ' <<
#define TT template <typename T>
using ll = long long;
using pii = pair<int, int>;
using pll = pair<ll, ll>;

TT bool chmin(T &x, T y) { return x > y ? (x = y, true) : false; }
TT bool chmax(T &x, T y) { return x < y ? (x = y, true) : false; }

TT using minheap = priority_queue<T, vector<T>, greater<T>>;
TT using maxheap = priority_queue<T>;

TT void print(vector<T> v, T x = 0) {
    int n = sz(v);
    rep(i, n) cout << v[i] + x << (i == n - 1 ? '\n' : ' ');
    if (n == 0) cout << '\n';
}

TT void printn(vector<T> v, T x = 0) {
    int n = sz(v);
    rep(i, n) cout << v[i] + x << '\n';
}

TT void rearrange(vector<T> &v) {
    sort(all(v));
    v.erase(unique(all(v)), end(v));
}

TT int lb(vector<T> &v, T x) { return lower_bound(all(v), x) - begin(v); }
TT int ub(vector<T> &v, T x) { return upper_bound(all(v), x) - begin(v); }

const int inf = (1 << 30) - 1;
const ll INF = (1LL << 60) - 1;

struct io_setup {
    io_setup() {
        ios_base::sync_with_stdio(false);
        cin.tie(NULL);
        cout << fixed << setprecision(15);
    }
} io_setup;

int main() {
    int n, m, q;
    cin >> n >> m >> q;
    vector<int> r(m);
    rep(i, m) cin >> r[i];
    vector<vector<int>> need(n, vector<int>(m, 0)), ac = need;
    rep(i, n) rep(j, m) cin >> need[i][j];
    vector<int> st(n, 0);
    vector<vector<int>> ls(n + 1);
    vector<vector<int>> rs(n + 1, r);
    rep(i, n) ls[0].eb(i);
    vector<int> fin(n, 0);
    queue<pair<pii, int>> que;
    auto sub = [&](int i, int j, int d) {
        rs[i][j] -= d;
        vector<int> nls;
        each(e, ls[i]) {
            if (!fin[e] && rs[i][j] < need[e][j]) {
                rep(k, m) if (ac[e][k]) que.emplace(pair(i + 1, k), ac[e][k]);
                ls[i + 1].eb(e);
                st[e]++;
            }
            else
                nls.eb(e);
        }
        swap(ls[i], nls);
    };
    rep2(t, 1, q + 1) {
        int x, y;
        cin >> x >> y, x--, y--;
        need[x][y]--, ac[x][y]++;
        fin[x] = 1;
        rep(j, m) fin[x] &= need[x][j] == 0;
        rep(i, st[x] + 1) {
            que.emplace(pair(i, y), 1);
            while (sz(que)) {
                auto [ij, d] = que.front();
                auto [i, j] = ij;
                que.pop();
                sub(i, j, d);
                if (sz(ls[i]) == 0 && sz(ls[i + 1]) > 0) {
                    cout << t << endl;
                    return 0;
                }
            }
        }
    }
    cout << -1 << endl;
}
accuracy: 0.14285714285714285
time_ms: 550
memory_kb: 3640
final_rank: 12

code_snippet: #include <bits/stdc++.h>
using namespace std;
using ll = long long;

const int MN = 300;
const int MR = 300;

void solve() {
  int n,r,q;
  cin >> n >> r >> q;
  vector<int> R(r);
  vector needs(n, vector<int>(r));
  vector<pair<int,int>> logs(q);
  for (int i=0;i<r;i++){
    cin >> R[i];
  }
  for (int i=0;i<n;i++){
    for (int j=0;j<r;j++){
      cin >> needs[i][j];
    }
  }
  for (int i=0;i<q;i++){
    int a,b;
    cin >> a >> b;
    --a,--b;
    logs[i] = {a,b};
  }
  auto f = [&](int t) -> bool {
    vector rel(n, vector<int>(r));
    vector<int> cur = R;
    set<int> worklist;
    for (int i=0;i<t;i++){
      cur[logs[i].second]--;
      rel[logs[i].first][logs[i].second]++;
    }
    for (int i=0;i<n;i++) worklist.insert(i);
    while (!worklist.empty()) {
      int next = -1;
      for (int i : worklist){
        bool ok = true;
        for (int j=0;j<r;j++){
          if (cur[j] + rel[i][j] < needs[i][j]) {
            ok = false;
            break;
          }
        }
        if (ok){
          next = i;
          break;
        }
      }
      if (next == -1)
        return true;
      worklist.erase(next);
      for (int j=0;j<r;j++){
        cur[j] += rel[next][j];
        rel[next][j]=0;
      }
    }
    return false;
  };

  int ng=-1,ok=q+1;
  while(ok-ng>1){
    int mid = (ng+ok)/2;
    if (f(mid)) ok = mid;
    else ng = mid;
  }
  if (ok == q + 1) {
    cout << -1 << "\n";
  } else {
    cout << ok << "\n";
  }
}

int main() {
  // #define LOCAL
  #ifdef LOCAL
  freopen("in", "r" , stdin);
  // freopen("output.txt", "w", stdout);
  #endif
  // cin.sync_with_stdio(false);
  // cin.tie(nullptr);

  solve();

  return 0;
}
accuracy: 0.03571428571428571
time_ms: 20
memory_kb: 3668
final_rank: 13

code_snippet: #pragma GCC optimize(2)
#include <iostream>
#include <iomanip>
#include <bitset>
#include <vector>
#include <string>
#include <math.h>
#include <cstring>
#include <stdio.h>
#include <cstring>
#include <stdlib.h>
#include <cstdlib>
#include <ctime>
#include <climits>
#include <cstdio>
#include <set>
#include <ctype.h>
#include <deque>
#include <string>
#include <map>
#include <utility>
#include <queue>
#include <vector>
#include <ctime>
#include <cctype>
#include <bitset>
#include <utility>
#include <sstream>
#include <complex>
#include <algorithm>
#include <iomanip>
#include <string.h>
#include <stack>
#include <assert.h>
#define fi first
#define se second
#define pb(a)  push_back(a)
#define Q 1000000
#define EXP  1.000000000000000
#define mod 1000000007
#define EPS 1E-12
#define m_p make_pair
#define ft first
#define PI 3.141592653589
#define sc second
typedef long long ll;
typedef unsigned long long ull;
using namespace std;
// const ll mod = 998244353;
inline ll add(int x)
{
    return (x+1);
}
inline ll gcd(ll a,ll b)
{
    if(b) while((a%=b) && (b%=a));
    return a+b;
}
inline __int128 read(){
    int x=0,a=1;
    char ch=getchar();
    while(ch<'0'||ch>'9'){
        if(ch=='-')
            a=-1;
        ch=getchar();
    }
    while(ch>='0'&&ch<='9'){
        x=(x<<1)+(x<<3)+(ch^48);
        ch=getchar();
    }
    return x*a;
}
inline void write(__int128 x){
    if(x<0){
        putchar('-');
        x=-x;
    }
    if(x>9) write(x/10);
    putchar(x%10+'0');
}
ll fastpow(ll a,ll b,ll p)
{
    ll res = 1;
    while (b > 0)
    {
        if(b & 1)
        {
            res = res * a % p;
        }
        a = a * a % p;;
        b >>= 1;
    }
    res %= p;
    return res;
}
int get_inv(int x)
{
    return fastpow(x,mod - 2,mod);
}
int n,m,t;
int now[310],sum[310],own[310],rem[310];
typedef struct node
{
    int x,y;
}Node;
Node s[200200];
int need[310][310];
int Need[310][310];
int pd[310];
int check(int x)
{
    int a,b;
    for(int i = 1;i <= m;i++){
        rem[i] = own[i];
    }
    for(int i = 1;i <= n;i++){
        for(int j = 1;j <= m;j++){
            Need[i][j] = need[i][j];
        }
    }
    for (int i = 1; i <= n; i++) {
        pd[i] = 1;
        now[i] = 0;
    }
    for (int i = 1; i <= x; i++) {
        a = s[i].x;
        b = s[i].y;
        now[a]++;
        Need[a][b]--;rem[b]--;
        if (now[a] == sum[a]) {
            for (int j = 1; j <= m; j++) {
                rem[j] += need[a][j];
            }
            pd[a] = 0;
        }
    }
    int flag = add(0);
    while (flag) {
        flag = 0;
        for (int i = 1; i <= n; i++) {
            if(pd[i]){
                int ttt = 0;
                for (int j = 1; j <= m; j++) {
                    if (Need[i][j] > rem[j]) {
                        ttt = 1;
                        break;
                    }
                }
                if (ttt == 0) {
                    for (int j = 1; j <= m; j++) {
                        rem[j] += need[i][j] - Need[i][j];
                    }
                    pd[i] = 0 ;
                    flag = 1;
                }
            }
        }
    }
    for (int i = 1; i <= n; i++) {
        if (pd[i]) {
            return  0;
        }
    }
    return 1;
}
int main(){
    cin>>n>>m>>t;
    for(int i = 1;i <= m;i++){
        scanf("%d",&own[i]);
    }
    for(int i = 1;i <= n;i++){
        for(int j = 1;j <= m;j++){
            scanf("%d",&need[i][j]);
            sum[i] += need[i][j];
        }
    }
    for(int i = add(0);i <= t;i++){
        scanf("%d%d",&s[i].x,&s[i].y);
    }
    if(check(t)){
        printf("-1\n");
    }
    else{
        int l = 0, r = t;
        while (l < r) {
            int mid = (l + r) >> 1 ;
            if (check(mid)) l = add(mid);
            else r = mid ;
        }
        printf("%d\n", l) ;
    }
    return 0;
}
accuracy: 1
time_ms: 20
memory_kb: 5448
final_rank: 1

code_snippet: #pragma GCC optimize(2)
#include <iostream>
#include <iomanip>
#include <bitset>
#include <vector>
#include <string>
#include <math.h>
#include <cstring>
#include <stdio.h>
#include <cstring>
#include <stdlib.h>
#include <cstdlib>
#include <ctime>
#include <climits>
#include <cstdio>
#include <set>
#include <ctype.h>
#include <deque>
#include <string>
#include <map>
#include <utility>
#include <queue>
#include <vector>
#include <ctime>
#include <cctype>
#include <bitset>
#include <utility>
#include <sstream>
#include <complex>
#include <algorithm>
#include <iomanip>
#include <string.h>
#include <stack>
#include <assert.h>
#define fi first
#define se second
#define pb(a)  push_back(a)
#define Q 1000000
#define EXP  1.000000000000000
#define mod 1000000007
#define EPS 1E-12
#define m_p make_pair
#define ft first
#define PI 3.141592653589
#define sc second
typedef long long ll;
typedef unsigned long long ull;
using namespace std;
// const ll mod = 998244353;
inline ll add(int x)
{
    return (x+1);
}
inline ll gcd(ll a,ll b)
{
    if(b) while((a%=b) && (b%=a));
    return a+b;
}
inline __int128 read(){
    int x=0,a=1;
    char ch=getchar();
    while(ch<'0'||ch>'9'){
        if(ch=='-')
            a=-1;
        ch=getchar();
    }
    while(ch>='0'&&ch<='9'){
        x=(x<<1)+(x<<3)+(ch^48);
        ch=getchar();
    }
    return x*a;
}
inline void write(__int128 x){
    if(x<0){
        putchar('-');
        x=-x;
    }
    if(x>9) write(x/10);
    putchar(x%10+'0');
}
ll fastpow(ll a,ll b,ll p)
{
    ll res = 1;
    while (b > 0)
    {
        if(b & 1)
        {
            res = res * a % p;
        }
        a = a * a % p;;
        b >>= 1;
    }
    res %= p;
    return res;
}
int get_inv(int x)
{
    return fastpow(x,mod - 2,mod);
}
int n,m,t;
int now[310],sum[310],own[310],rem[310];
typedef struct node
{
    int x,y;
}Node;
Node s[200200];
int need[310][310];
int Need[310][310];
int pd[310];
int check(int x)
{
    int a,b;
    for(int i = 1;i <= m;i++){
        rem[i] = own[i];
    }
    for(int i = 1;i <= n;i++){
        for(int j = 1;j <= m;j++){
            Need[i][j] = need[i][j];
        }
    }
    for (int i = 1; i <= n; i++) {
        pd[i] = 1;
        now[i] = 0;
    }
    for (int i = 1; i <= x; i++) {
        a = s[i].x;
        b = s[i].y;
        now[a]++;
        Need[a][b]--;rem[b]--;
        if (now[a] == sum[a]) {
            for (int j = 1; j <= m; j++) {
                rem[j] += need[a][j];
            }
            pd[a] = 0;
        }
    }
    int flag = 1;
    while (flag) {
        flag = 0;
        for (int i = 1; i <= n; i++) {
            if(pd[i]){
                int ttt = 0;
                for (int j = 1; j <= m; j++) {
                    if (Need[i][j] > rem[j]) {
                        ttt = 1;
                        break;
                    }
                }
                if (ttt == 0) {
                    for (int j = 1; j <= m; j++) {
                        rem[j] += need[i][j] - Need[i][j];
                    }
                    pd[i] = 0 ;
                    flag = 1;
                }
            }
        }
    }
    for (int i = 1; i <= n; i++) {
        if (pd[i]) {
            return  0;
        }
    }
    return 1;
}
int main(){
    cin>>n>>m>>t;
    for(int i = 1;i <= m;i++){
        scanf("%d",&own[i]);
    }
    for(int i = 1;i <= n;i++){
        for(int j = 1;j <= m;j++){
            scanf("%d",&need[i][j]);
            sum[i] += need[i][j];
        }
    }
    for(int i = 1;i <= t;i++){
        scanf("%d%d",&s[i].x,&s[i].y);
    }
    if(check(t)){
        printf("-1\n");
    }
    else{
        int l = 0, r = t;
        while (l < r) {
            int mid = (l + r) >> 1 ;
            if (check(mid)) l = mid + 1 ;
            else r = mid ;
        }
        printf("%d\n", l) ;
    }
    return 0;
}
accuracy: 1
time_ms: 20
memory_kb: 5508
final_rank: 2

code_snippet: #include <map>
#include <set>
#include <ctime>
#include <queue>
#include <stack>
#include <cmath>
#include <vector>
#include <bitset>
#include <cstdio>
#include <cctype>
#include <string>
#include <numeric>
#include <cstring>
#include <cassert>
#include <climits>
#include <cstdlib>
#include <iostream>
#include <algorithm>
#include <functional>
using namespace std ;
//#define int long long
#define rep(i, a, b) for (int i = (a); i <= (b); i++)
#define per(i, a, b) for (int i = (a); i >= (b); i--)
#define loop(it, v) for (auto it = v.begin(); it != v.end(); it++)
#define cont(i, x) for (int i = head[x]; i; i = e[i].nxt)
#define clr(a) memset(a, 0, sizeof(a))
#define ass(a, sum) memset(a, sum, sizeof(a))
#define lowbit(x) (x & -x)
#define all(x) x.begin(), x.end()
#define SC(t, x) static_cast <t> (x)
#define ub upper_bound
#define lb lower_bound
#define pqueue priority_queue
#define mp make_pair
#define pb push_back
#define pof pop_front
#define pob pop_back
#define fi first
#define se second
#define y1 y1_
#define Pi acos(-1.0)
#define iv inline void
#define enter cout << endl
#define siz(x) ((int)x.size())
#define file(x) freopen(x".in", "r", stdin),freopen(x".out", "w", stdout)
typedef double db ;
typedef long long ll ;
typedef unsigned long long ull ;
typedef pair <int, int> pii ;
typedef vector <int> vi ;
typedef vector <pii> vii ;
typedef queue <int> qi ;
typedef queue <pii> qii ;
typedef set <int> si ;
typedef map <int, int> mii ;
typedef map <string, int> msi ;
const int N = 310 ;
const int M = 200010 ;
const int INF = 0x3f3f3f3f ;
const int iinf = 1 << 30 ;
const ll linf = 2e18 ;
const int MOD = 1000000007 ;
const double eps = 1e-7 ;
void douout(double x){ printf("%lf\n", x + 0.0000000001) ; }
template <class T> void print(T a) { cout << a << endl ; exit(0) ; }
template <class T> void chmin(T &a, T b) { if (a > b) a = b ; }
template <class T> void chmax(T &a, T b) { if (a < b) a = b ; }
template <class T> void add(T &a, T b) { a = (1ll * a + b) % MOD ; }
template <class T> void sub(T &a, T b) { a = (a - b + MOD) % MOD ; }
template <class T> void mul(T &a, T b) { a = (ll) a * b % MOD ; }
template <class T> T read() {
    int f = 1 ; T x = 0 ;
    char ch = getchar() ;
    while (!isdigit(ch)) { if (ch == '-') f = -1 ; ch = getchar() ; }
    while (isdigit(ch)) { x = x * 10 + ch -'0' ; ch = getchar() ; }
    return x * f ;
}

int n, m, p ;
int now[N], sum[N], has[N], rem[N], ax[M], ay[M] ;
int need[N][N], Need[N][N] ;
bool inq[N] ;

bool check(int t) {
    int a, b ;
    rep(i, 1, m) rem[i] = has[i] ;
    rep(i, 1, n)
    rep(j, 1, m)
    Need[i][j] = need[i][j] ;
    rep(i, 1, n) inq[i] = 1, now[i] = 0 ;
    rep(i, 1, t) {
        a = ax[i], b = ay[i] ;
        now[a]++, Need[a][b]--, rem[b]-- ;
        if (now[a] == sum[a]) {
            rep(j, 1, m) rem[j] += need[a][j] ;
            inq[a] = 0 ;
        }
    }
    bool flg = 1 ;
    while (flg) {
        flg = 0 ;
        rep(i, 1, n)
        if (inq[i]) {
            int j ;
            for (j = 1; j <= m; j++) if (Need[i][j] > rem[j]) break ;
            if (j > m) {
                rep(j, 1, m) rem[j] += need[i][j] - Need[i][j] ;
                inq[i] = 0 ; flg = 1 ;
            }
        }
    }
    rep(i, 1, n) if (inq[i]) return 0 ;
    return 1 ;
}
signed main() {
    scanf("%d%d%d", &n, &m, &p) ;
    rep(i, 1, m) scanf("%d", &has[i]) ;
    rep(i, 1, n)
    rep(j, 1 ,m)
    scanf("%d", &need[i][j]), sum[i] += need[i][j] ;
    rep(i, 1, p) scanf("%d%d", &ax[i], &ay[i]) ;
    if (check(p)) print("-1") ; // 特判
    int l = 0, r = p ;
    while (l < r) {
        int mid = (l + r) >> 1 ;
        if (check(mid)) l = mid + 1 ;
        else r = mid ;
    }
    printf("%d\n", l) ;
    return 0 ;
}
accuracy: 1
time_ms: 20
memory_kb: 5512
final_rank: 3

code_snippet: #pragma GCC optimize(2)
#include <iostream>
#include <iomanip>
#include <bitset>
#include <vector>
#include <string>
#include <math.h>
#include <cstring>
#include <stdio.h>
#include <cstring>
#include <stdlib.h>
#include <cstdlib>
#include <ctime>
#include <climits>
#include <cstdio>
#include <set>
#include <ctype.h>
#include <deque>
#include <string>
#include <map>
#include <utility>
#include <queue>
#include <vector>
#include <ctime>
#include <cctype>
#include <bitset>
#include <utility>
#include <sstream>
#include <complex>
#include <algorithm>
#include <iomanip>
#include <string.h>
#include <stack>
#include <assert.h>
#define fi first
#define se second
#define pb(a)  push_back(a)
#define Q 1000000
#define EXP  1.000000000000000
#define mod 1000000007
#define EPS 1E-12
#define m_p make_pair
#define ft first
#define PI 3.141592653589
#define sc second
typedef long long ll;
typedef unsigned long long ull;
using namespace std;
// const ll mod = 998244353;
inline ll add(int x)
{
    return (x+1);
}
inline ll gcd(ll a,ll b)
{
    if(b) while((a%=b) && (b%=a));
    return a+b;
}
inline __int128 read(){
    int x=0,a=1;
    char ch=getchar();
    while(ch<'0'||ch>'9'){
        if(ch=='-')
            a=-1;
        ch=getchar();
    }
    while(ch>='0'&&ch<='9'){
        x=(x<<1)+(x<<3)+(ch^48);
        ch=getchar();
    }
    return x*a;
}
inline void write(__int128 x){
    if(x<0){
        putchar('-');
        x=-x;
    }
    if(x>9) write(x/10);
    putchar(x%10+'0');
}
ll fastpow(ll a,ll b,ll p)
{
    ll res = 1;
    while (b > 0)
    {
        if(b & 1)
        {
            res = res * a % p;
        }
        a = a * a % p;;
        b >>= 1;
    }
    res %= p;
    return res;
}
int get_inv(int x)
{
    return fastpow(x,mod - 2,mod);
}
int p,r,t;
int ori_need[310][310];
int tneed[310][310];
int tavail[310];
int ttrem[310];
typedef struct node
{
    int p,r;
}Node;
Node s[200200];
typedef struct hello
{
    int need[310][310];
    int apply[310];
    int avail[310];
    int term[310];
    inline void acquire(int x,int y){
        need[x][y]--;
        apply[x]--;
        avail[y]--;
        if(apply[x] == 0){
            term[x] = (int)add(0);
            for (int i = (int)add(0); i <= r; i++)
            {
                avail[i] += ori_need[x][i];
            }
        }
    }
    inline void transcript(){
        memcpy(tneed,need,sizeof(need));
        memcpy(tavail,avail,sizeof(avail));
        memcpy(ttrem,term,sizeof(term));
    }
    inline int valid()
    {
        int flag = 0;
        int release;
        transcript();
        while (flag == 0) {
            flag = 1;
            for(int i = 1;i <= p;i++){
                if(ttrem[i] == 0){
                    release = 1;
                    for(int j = 1;j <= r;j++){
                        if(tneed[i][j] > tavail[j]){
                            release = 0;
                            break;
                        }
                    }
                    if(release == 1){
                        ttrem[i] = 1;
                        for(int j = 1;j <= r;j++){
                            tavail[j] += ori_need[i][j] - tneed[i][j];
                        }
                        flag = 0;
                    }
                }
            }
        }
        for (int i = 1; i <= p; i++)
        {
            if(ttrem[i] == 0){
                return 0;
            }
        }
        return 1;
    }
}Statu;
Statu last,now;

int main(){
    cin>>p>>r>>t;
    for (int i = 1; i <= r; i++)
    {
        scanf("%d",&last.avail[i]);
    }
    for(int i = 1;i <= p;i++){
        last.term[i] = last.apply[i] = 0;
    }
    for(int i = 1;i <= p;i++){
        for(int j = 1;j <= r;j++){
            scanf("%d",&ori_need[i][j]);
            last.need[i][j] = ori_need[i][j];
        }
    }
    for(int i = 1;i <= t;i++){
        scanf("%d%d",&s[i].p,&s[i].r);
    }
    last.acquire(s[1].p,s[1].r);
    ll L,R,mid;
    L = 1;
    R = add(t);
    mid = (L + R) >> 1;
    while (L + 1 < R)
    {
        mid = (L + R) >> 1;
        now = last;
        for(ll i = L + 1;i <= mid;i++){
            now.acquire(s[i].p,s[i].r);
        }
        if(now.valid() == 1){
            last = now;
            L = mid;
        }
        else{
            R = mid;
        }
    }
    if(R > t){
        printf("-1\n");
    }
    else{
        printf("%lld\n",R);
    }
    return 0;
}
accuracy: 0.03571428571428571
time_ms: 10
memory_kb: 5316
final_rank: 18

code_snippet: #include <bits/stdc++.h>
using namespace std;
int main(){
  int p, r, t;
  cin >> p >> r >> t;
  vector<int> l(r);
  for (int i = 0; i < r; i++){
    cin >> l[i];
  }
  vector<vector<int>> n(p, vector<int>(r));
  for (int i = 0; i < p; i++){
    for (int j = 0; j < r; j++){
      cin >> n[i][j];
    }
  }
  vector<int> P(t), R(t);
  for (int i = 0; i < t; i++){
    cin >> P[i] >> R[i];
    P[i]--;
    R[i]--;
  }
  int fv = 0, tv = t + 1;
  while (tv - fv > 1){
    int mid = (tv + fv) / 2;
    vector<vector<int>> c(p, vector<int>(r, 0));
    vector<bool> used(p, false);
    vector<int> l2 = l;
    for (int i = 0; i < mid; i++){
      c[P[i]][R[i]]++;
      l2[R[i]]--;
      bool ok = true;
      for (int j = 0; j < r; j++){
        if (c[P[i]][j] < n[P[i]][j]){
          ok = false;
          break;
        }
      }
      if (ok){
        used[P[i]] = true;
        for (int j = 0; j < r; j++){
          l2[j] += n[P[i]][j];
        }
      }
    }
    while (true){
      int nxt = -1;
      for (int i = 0; i < p; i++){
        if (!used[i]){
          bool ok = true;
          for (int j = 0; j < r; j++){
            if (n[i][j] - c[i][j] > l2[j]){
              ok = false;
            }
          }
          if (ok){
            nxt = i;
            break;
          }
        }
      }
      if (nxt == -1){
        break;
      }
      used[nxt] = true;
      for (int i = 0; i < r; i++){
        l2[i] += c[nxt][i];
      }
    }
    bool ok = true;
    for (int i = 0; i < p; i++){
      if (!used[i]){
        ok = false;
      }
    }
    if (ok){
      fv = mid;
    } else {
      tv = mid;
    }
  }
  if (tv == t + 1){
    cout << -1 << endl;
  } else {
    cout << tv << endl;
  }
}
accuracy: 1
time_ms: 130
memory_kb: 5132
final_rank: 8

code_snippet: #include <bits/stdc++.h>
using namespace std;
int main(){
  int p, r, t;
  cin >> p >> r >> t;
  vector<int> l(r);
  for (int i = 0; i < r; i++){
    cin >> l[i];
  }
  vector<vector<int>> n(p, vector<int>(r));
  for (int i = 0; i < p; i++){
    for (int j = 0; j < r; j++){
      cin >> n[i][j];
    }
  }
  vector<int> P(t), R(t);
  for (int i = 0; i < t; i++){
    cin >> P[i] >> R[i];
    P[i]--;
    R[i]--;
  }
  int fv = 0, tv = t + 1;
  while (tv - fv > 1){
    int mid = (tv + fv) / 2;
    vector<vector<int>> c(p, vector<int>(r, 0));
    vector<int> l2 = l;
    for (int i = 0; i < mid; i++){
      c[P[i]][R[i]]++;
      l2[R[i]]--;
    }
    vector<bool> used(p, false);
    for (int i = 0; i < p; i++){
      int nxt = -1;
      for (int j = 0; j < p; j++){
        if (!used[j]){
          bool ok = true;
          for (int k = 0; k < r; k++){
            if (n[j][k] - c[j][k] > l2[k]){
              ok = false;
            }
          }
          if (ok){
            nxt = j;
          }
        }
      }
      if (nxt == -1){
        break;
      }
      used[nxt] = true;
      for (int k = 0; k < r; k++){
        l2[k] += c[nxt][k];
      }
    }
    bool ok = true;
    for (int i = 0; i < p; i++){
      if (!used[i]){
        ok = false;
      }
    }
    if (ok){
      fv = mid;
    } else {
      tv = mid;
    }
  }
  if (tv == t + 1){
    cout << -1 << endl;
  } else {
    cout << tv << endl;
  }
}
accuracy: 0.03571428571428571
time_ms: 30
memory_kb: 3552
final_rank: 17

code_snippet: #include <bits/stdc++.h>
using namespace std;
int main(){
  int p, r, t;
  cin >> p >> r >> t;
  vector<int> l(r);
  for (int i = 0; i < r; i++){
    cin >> l[i];
  }
  vector<vector<int>> n(p, vector<int>(r));
  for (int i = 0; i < p; i++){
    for (int j = 0; j < r; j++){
      cin >> n[i][j];
    }
  }
  vector<int> P(t), R(t);
  for (int i = 0; i < t; i++){
    cin >> P[i] >> R[i];
    P[i]--;
    R[i]--;
  }
  int fv = 0, tv = t + 1;
  while (tv - fv > 1){
    int mid = (tv + fv) / 2;
    vector<vector<int>> c(p, vector<int>(r, 0));
    vector<int> l2 = l;
    for (int i = 0; i < mid; i++){
      c[P[i]][R[i]]++;
      l2[R[i]]--;
    }
    vector<bool> used(p, false);
    for (int i = 0; i < p; i++){
      int nxt = -1;
      for (int j = 0; j < p; j++){
        if (!used[j]){
          bool ok = true;
          for (int k = 0; k < r; k++){
            if (n[j][k] - c[j][k] > l2[k]){
              ok = false;
            }
          }
          if (ok){
            nxt = j;
          }
        }
      }
      if (nxt == -1){
        break;
      }
      used[nxt] = true;
      for (int j = 0; j < p; j++){
        for (int k = 0; k < r; k++){
          l2[k] += c[j][k];
        }
      }
    }
    bool ok = true;
    for (int i = 0; i < p; i++){
      if (!used[i]){
        ok = false;
      }
    }
    if (ok){
      fv = mid;
    } else {
      tv = mid;
    }
  }
  if (tv == t + 1){
    cout << -1 << endl;
  } else {
    cout << tv << endl;
  }
}
accuracy: 0.03571428571428571
time_ms: 30
memory_kb: 3492
final_rank: 16

code_snippet: #include <bits/stdc++.h>
using namespace std;
const int INF = 0x3fffffff;
void chmin(int& a, int b){ if(a > b) a = b; }

int main(){
    int p, r, t;
    cin >> p >> r >> t;
    vector<int> l(r);
    for(int& i : l) cin >> i;
    vector n(p, vector<int>(r));
    for(auto& i : n) for(auto& j : i) cin >> j;
    vector use(p, vector{pair{0, vector<int>(r)}});
    for(int i = 1; i <= t; i++){
        int P, R;
        cin >> P >> R;
        P--; R--;
        use[P].emplace_back(i, use[P].back().second);
        use[P].back().second[R]++;
        if(use[P].back().second == n[P]){
            fill(n[P].begin(), n[P].end(), 0);
            use[P].resize(1);
        }
    }
    int ok = 0, ng = t + 1;
    auto check = [&](int t) -> bool {
        vector need = n;
        vector available = l;
        vector<vector<int>::iterator> u(p);
        for(int i = 0; i < p; i++){
            u[i] = prev(upper_bound(use[i].begin(), use[i].end(), pair{t + 1, vector<int>{}}))->second.begin();
            for(int j = 0; j < r; j++){
                need[i][j] -= u[i][j];
                available[j] -= u[i][j];
            }
        }
        vector<bool> finish(p);
        int cnt = 0;
        while(cnt < p){
            bool f = 1;
            for(int i = 0; i < p; i++){
                if(finish[i]) continue;
                if([&]{
                    for(int j = 0; j < r; j++) if(available[j] < need[i][j]) return 0;
                    return 1;
                }()){
                    f = 0;
                    cnt++;
                    finish[i] = 1;
                    for(int j = 0; j < r; j++) available[j] += u[i][j];
                }
            }
            if(f) return 0;
        }
        return 1;
    };
    while(abs(ok - ng) > 1){
        int cen = (ok + ng) / 2;
        (check(cen) ? ok : ng) = cen;
    }
    if(ng == t + 1) ng = -1;
    cout << ng << endl;
}
accuracy: 1
time_ms: 70
memory_kb: 41368
final_rank: 10

code_snippet: #include <bits/stdc++.h>
using namespace std;
const int INF = 0x3fffffff;
void chmin(int& a, int b){ if(a > b) a = b; }

int main(){
    int p, r, t;
    cin >> p >> r >> t;
    vector<int> l(r);
    for(int& i : l) cin >> i;
    vector n(p, vector<int>(r));
    vector use(p, vector{pair{0, vector<int>(r)}});
    for(auto& i : n) for(auto& j : i) cin >> j;
    for(int i = 1; i <= t; i++){
        int P, R;
        cin >> P >> R;
        P--; R--;
        use[P].emplace_back(i, use[P].back().second);
        use[P].back().second[R]++;
    }
    int ok = 0, ng = t + 1;
    auto check = [&](int t) -> bool {
        vector need = n;
        vector available = l;
        vector<vector<int>::iterator> u(p);
        for(int i = 0; i < p; i++){
            u[i] = prev(upper_bound(use[i].begin(), use[i].end(), pair{t + 1, vector<int>{}}))->second.begin();
            for(int j = 0; j < r; j++){
                need[i][j] -= u[i][j];
                available[j] -= u[i][j];
            }
        }
        vector<bool> finish(p);
        int cnt = 0;
        while(cnt < p){
            bool f = 1;
            for(int i = 0; i < p; i++){
                if(finish[i]) continue;
                if([&]{
                    for(int j = 0; j < r; j++) if(available[j] < need[i][j]) return 0;
                    return 1;
                }()){
                    f = 0;
                    cnt++;
                    finish[i] = 1;
                    for(int j = 0; j < r; j++) available[j] += u[i][j];
                }
            }
            if(f) return 0;
        }
        return 1;
    };
    while(abs(ok - ng) > 1){
        int cen = (ok + ng) / 2;
        (check(cen) ? ok : ng) = cen;
    }
    if(ng == t + 1) ng = -1;
    cout << ng << endl;
}
accuracy: 0.03571428571428571
time_ms: 30
memory_kb: 47828
final_rank: 20

code_snippet: #include "iostream"
#include "climits"
#include "list"
#include "queue"
#include "stack"
#include "set"
#include "functional"
#include "algorithm"
#include "string"
#include "map"
#include "unordered_map"
#include "unordered_set"
#include "iomanip"
#include "cmath"
#include "random"
#include "bitset"
#include "cstdio"
#include "numeric"
#include "cassert"
#include "ctime"

using namespace std;

//constexpr long long int MOD = 1000000007;
//constexpr int MOD = 1000000007;
//constexpr int MOD = 998244353;
constexpr long long int MOD = 998244353;
constexpr double EPS = 1e-8;

//int N, M, K, T, H, W, L, R;
long long int N, M, K, T, H, W, L, R;



int main() {
	ios::sync_with_stdio(false);
	cin.tie(0);

	cin >> N >> M >> K;
	vector<int>v(M);
	for (auto &i : v)cin >> i;
	vector<vector<int>>cost(N, vector<int>(M));
	for (auto &i : cost)for (auto &j : i)cin >> j;
	vector<pair<int, int>>w(K);
	for (auto &i : w) {
		cin >> i.first >> i.second;
		i.first--;
		i.second--;
	}
	int ok = 0, ng = K + 1;
	while (ng - ok > 1) {
		int mid = (ok + ng) / 2;
		auto c = cost;
		auto amari = v;
		for (int i = 0; i < mid; i++) {
			if (amari[w[i].second]) {
				amari[w[i].second]--;
				c[w[i].first][w[i].second]--;
				if (!*max_element(c[w[i].first].begin(), c[w[i].first].end())) {
					c[w[i].first] = cost[w[i].first];
					for (int j = 0; j < M; j++) {
						amari[j] += cost[w[i].first][j];
					}
				}
			}
		}
		vector<int>used(N);
		queue<int>Q;
		for (int i = 0; i < N; i++) {
			bool ok = true;
			for (int j = 0; j < M; j++) {
				if (amari[j] < c[i][j]) {
					ok = false;
				}
			}
			if (ok) {
				used[i] = 1;
				Q.push(i);
			}
		}
		while (!Q.empty()) {
			int cn = Q.front();
			Q.pop();
			for (int j = 0; j < M; j++) {
				amari[j] += cost[cn][j] - c[cn][j];
			}
			for (int i = 0; i < N; i++) {
				if (used[i])continue;
				bool ok = true;
				for (int j = 0; j < M; j++) {
					if (amari[j] < c[i][j]) {
						ok = false;
					}
				}
				if (ok) {
					used[i] = 1;
					Q.push(i);
				}
			}
		}
		if (*min_element(used.begin(), used.end())) {
			ok = mid;
		}
		else {
			ng = mid;
		}
	}
	if (ng == K + 1)ng = -1;
	cout << ng << endl;
}
accuracy: 1
time_ms: 490
memory_kb: 5408
final_rank: 9