When CF goes down to 0, it's just a bunker. Both questions are correct, but they are useless. Write a problem-solving report to record your mental journey.
Question A is how many K knives are cut on the rectangle of an n * m square. It is not difficult to find that if the vertical cutting K1 and horizontal cutting K2, the answer should be (N/(K1 + 1) * (M/(k2 + 1 )), division is an integer. Although it is an integer, it is not difficult to find that it is actually the smallest (K1 + 1) * (k2 + 1). According to the mean inequality, K1 + k2 = K (fixed value) when k1 = k2 (K1 + 1) * (k2 + 1) = K1 * k2 + k1 + k2 + 1 = K1 * k2 + k + 1 should be the maximum value, therefore, when K1 and K2 are closer to the two ends, this value will be minimized. Therefore, we always cut a certain one-dimensional, and then consider the remaining one-dimensional. I was wrong when I was playing the game, ah...
Question B is to give you a picture, some of which are common edges, some are train route edges, and the train route edges are connected from capital 1 to other vertices, the question is how many lines can be removed from the train route edge so that the shortest path length of each point remains unchanged. The idea is that if we can reach a certain point by taking another point, this edge is not needed. When we leave the edge, we will update ans, which leads to a much smaller answer.
#pragma warning(disable:4996)#include <iostream>#include <cstdio>#include <vector>#include <cstring>#include <string>#include <algorithm>#include <cmath>#include <queue>using namespace std;#define ll long long#define maxn 105000#define inf 10000000000000000LLint n, m, k;struct Edge{int v;ll w;Edge(int vi, ll wi) : v(vi), w(wi){}Edge(){}};vector<Edge>G[maxn];ll dis2[maxn];ll ans = 0;ll d[maxn];bool in[maxn];void spfa(){memset(d, 0x3f, sizeof(d));memset(in, 0, sizeof(in));queue<int> que;que.push(1); in[1] = true;d[1] = 0;while (!que.empty()){int u = que.front(); que.pop(); in[u] = false;for (int i = 0; i < G[u].size(); i++){int v = G[u][i].v; ll w = G[u][i].w;if (d[u] + w < d[v]){d[v] = d[u] + w;if (!in[v]) que.push(v), in[v] = true;}}}}ll d2[maxn];bool upd[maxn];void spfa2(){memset(d2, 0x3f, sizeof(d2));memset(in, 0, sizeof(in));queue<int> que;que.push(1); d2[1] = 0; in[1] = true;for (int i = 2; i <= n; i++){if (dis2[i] < d[i]){que.push(i); in[i] = true; d2[i] = dis2[i];}}while (!que.empty()){int u = que.front(); que.pop(); in[u] = false;for (int i = 0; i < G[u].size(); i++){int v = G[u][i].v; ll w = G[u][i].w;if (d2[u] + w < d2[v]){d2[v] = d2[u] + w;if (!in[v]) que.push(v), in[v] = true;if (upd[v]) {++ans; upd[v] = false;}}else if (d2[u] + w == d2[v]){if (upd[v]) {++ans; upd[v] = false;}}}}}int main(){while (cin >> n >> m >> k){for (int i = 0; i <= n; i++) G[i].clear();memset(dis2, 0x3f, sizeof(dis2));ans = 0;int ui, vi; ll wi;for (int i = 0; i < m; i++){scanf("%d%d%I64d", &ui, &vi, &wi);G[ui].push_back(Edge(vi, wi));G[vi].push_back(Edge(ui, wi));}spfa();memcpy(dis2, d, sizeof(dis2));memset(upd, 0, sizeof(upd));int si; ll yi;for (int i = 0; i < k; i++){scanf("%d%I64d", &si, &yi);if (dis2[si] <= yi) ++ans;else {dis2[si] = yi; if (upd[si]) {++ans;}upd[si] = true;}}spfa2();cout << ans << endl;}return 0;}