#include using namespace std; #include using mint = atcoder::modint998244353; #define rep(i, l, r) for (int i = (l); i < (r); i++) #define ll long long #define all(x) (x).begin(), (x).end() #define siz(x) (int)x.size() #define debug(x) cout << #x << " : " << endl; for (auto u : x) cout << u << " "; cout << endl template bool chmin(T& a, T b) { if (a > b) { a = b; return 1; } return 0; } template bool chmax(T& a, T b) { if (a < b) { a = b; return 1; } return 0; } const int inf = 1e9; const ll INF = 4e18; template using spq = priority_queue, greater>; vector di = {1, 0, -1, 0}, dj = {0, 1, 0, -1}; int main() { int N, M, K; cin >> N >> M >> K; int R = N * (N - 1) / 2 - M; if (R < N - 1) { cout << "No\n"; return 0; } // vector A(K + 1, 1); // auto score = [&](vector X) -> int { // int ret = 0; // rep(i, 0, K) ret += A[i] * A[i + 1]; // rep(i, 0, K + 1) ret += A[i] * (A[i] - 1) / 2; // return ret; // }; // rep(_, 0, N - K - 1) { // int amx = -1, mx = -1; // rep(j, 1, K + 1) { // A[j]++; // if (chmax(mx, score(A))) amx = j; // A[j]--; // } // A[amx]++; // } //謎の貪欲をしなくてもdpできますやん!! //i, used, last vector dp(K + 1, vector(N + 1, vector(N + 1, -1))); vector from(K + 1, vector(N + 1, vector(N + 1, -1))); dp[0][1][1] = 0; rep(i, 0, K) { rep(j, 0, N + 1) rep(k, 0, N + 1) { if (dp[i][j][k] == -1) continue; rep(l, 1, N + 1) { if (j + l <= N) { if (chmax(dp[i + 1][j + l][l], dp[i][j][k] + k * l + l * (l - 1) / 2)) { from[i + 1][j + l][l] = k; } } } } } int ci = K, cj = 0, ck = 0; rep(j, 0, N + 1) rep(k, 0, N + 1) { if (dp[K][j][k] > dp[ci][cj][ck]) { cj = j; ck = k; } } int sc = dp[K][cj][ck]; vector A; while(true) { A.push_back(ck); int memo = from[ci][cj][ck]; ci--; cj -= ck; ck = memo; if (ci == -1) break; } reverse(all(A)); if (R <= sc) { cout << "Yes\n"; vector> V(K + 1); int c = 0; rep(i, 0, K + 1) { rep(_, 0, A[i]) V[i].push_back(c++); } vector> choose(N, vector(N, false)); vector> choosable; rep(i, 0, K) { rep(j, 0, A[i]) rep(k, 0, A[i + 1]) { if (j == 0) { choose[V[i][j]][V[i + 1][k]] = true; } else { choosable.push_back({V[i][j], V[i + 1][k]}); } } } rep(i, 0, K + 1) { rep(j, 0, A[i]) rep(k, j + 1, A[i]) { choosable.push_back({V[i][j], V[i][k]}); } } // cout << "choosable : " << "\n"; // for (auto[u, v] : choosable) { // cout << u << " " << v << "\n"; // } // cout << "====" << endl; int chosen = N - 1; // assert(siz(choosable) >= R - chosen);s rep(i, 0, R - chosen) { auto[u, v] = choosable[i]; choose[u][v] = true; } rep(i, 0, N) rep(j, i + 1, N) { if (not choose[i][j]) cout << i + 1 << " " << j + 1 << "\n"; } } else { cout << "No\n"; } }