[Preparing for the Lanqiao Cup] The 14th Lanqiao Cup Provincial Competition C/C++ Group B real questions and solutions

After participating in two Lanqiao Cups and taking the real questions of previous years, my intuitive feeling is that the Lanqiao Cup is no longer so "violent", but gradually tends to DP and search element graph theory. The following are the real questions and solutions of C/C++ Group B of the 14th Lanqiao Cup Provincial Competition. I hope it will be helpful to you who are reading.

topic

Test question A: Date statistics

[Problem Description]
Xiao Lan now has an array with a length of 100, and the value of each element in the array is in the range of 0 to 9. The elements in the array are as follows from left to right:
5 6 8 6 9 1 6 1 2 4 9 1 9 8 2 3 6 4 7 7 5 9 5 0 3 8 7 5 8 1 5 8 6 1 8 3 0 3 7 9 2 7 0 5 8 8 5 7 0 9 9 1 9 4 4 6 8 6 3 3 8 5 1 6 3 4 6 7 0 7 8 2 7 6 8 9 5 6 5 6 1 4 0 1 0 0 9 4 8 0 9 1 2 8 5 0 2 5 3 3
Now he wants to find some subsequences from this array that meet the following conditions:

  1. The length of the subsequence is 8;
  2. This subsequence can form a date in yyyymmdd format in subscript order, and
    requires that this date be a date on a certain day in 2023, such as 20230902, 20231223.
    yyyy represents the year, mm represents the month, and dd represents the number of days. When the length of the month or day has only
    one digit, a leading zero is required.
    Please help Xiaolan calculate how many different dates in 2023 can be found based on the above conditions.
    You only need to count the same date once.

【Answer submission】
This is a fill-in-the-blank question. You only need to calculate the result and submit it. The result of this question is an integer. Only fill in this integer when submitting the answer. No points will be awarded for filling in extra content.

Test question B: 01 Entropy of string

Insert image description here

Test question C: Smelting metals

[Problem Description]
Xiao Lan has a magical furnace that is used to smelt ordinary metal O into a special metal X. This
furnace has an attribute V called the conversion rate. V is a positive integer, which means that it consumes V ordinary gold
and the attribute O can be smelted. A special metal X cannot
continue to be smelted when the number of ordinary metals O is less than V.
Now N smelting records are given, each record contains two integers A and B, which means that this time
A ordinary metal O was invested , and finally smelted B special metals X. Each record is independent, which means that the ordinary metal O that was not consumed last time will not be added to the next smelting. Based on these N smelting records, please guess what the minimum and maximum values ​​of the conversion rate V may be respectively. The question guarantees that the evaluation data does not exist. solution situation. [Input format] The first line contains an integer N, which represents the number of smelting records. Next, enter N lines, each line contains two integers A and B. The meaning is as stated in the title. [Output format] Output two integers, representing the possible minimum and maximum values ​​of V respectively, separated by spaces. [Sample input] 3 75 3 53 2 59 2[Sample output] 20 25















Insert image description here

Question D: Plane landing

[Problem Description]
N planes are preparing to land at an airport with only one runway. Among them, the i-th aircraft arrives at the airport at time Ti
. When it arrives, its remaining fuel can continue to hover for Di units of time, that is, it can fly at the earliest
The landing starts at time Ti, and can start landing at time Ti + Di at the latest. The landing process takes Li
units of time.
When one plane completes landing, another plane can immediately start landing at the same time, but it cannot
start landing before the previous plane completes landing. .
Please judge whether all N planes can land safely.
[Input format]
The input contains multiple sets of data.
The first line contains an integer T, representing the number of groups of test data.
For each set of data, the first row contains an integer N.
The following N lines, each containing three integers: Ti, Di and Li.
[Output format]
For each set of data, output YES or NO, indicating whether all can land safely.
[Sample input]
2
3
0 100 10
10 10 10
0 2 20
3
0 10 20
10 10 20
20 10 20
[Sample output]
YES
NO
[Example description]
For the first set of data, you can arrange for the third aircraft to start landing at time 0 and complete the landing at time 20< a i=30> fall. Arrange for the second plane to start landing at 20:00 and complete the landing at 30:00. Arrange for the first plane to start landing at 30:00 and complete the landing at 40:00. For the second set of data, no matter how arranged, there will be planes that cannot land in time. [Evaluation use case scale and convention] For 30% of the data, N ≤ 2. For 100% of the data, 1 ≤ T ≤ 10, 1 ≤ N ≤ 10, 0 ≤ Ti, Di, Li ≤ 10





Test question E: Solitaire sequence

[Problem Description]
For an integer sequence of length K: A1, A2, . . . , AK, we call it a solitaire sequence when and< a i=2> Only if the first digit of Ai is exactly equal to the last digit of Ai−1 (2 ≤ i ≤ K). For example, 12, 23, 35, 56, 61, 11 is a solitaire sequence; 12, 23, 34, 56 is not a solitaire sequence because the first digit of 56 The last digit is not equal to 34. All integer sequences of length 1 are solitaire sequences. Now given a sequence A1, A2, . . . , AN of length N, please calculate the minimum number of to delete from it so that the remaining The sequence below is a Solitaire sequence? [Input format] The first line contains an integer N. The second line contains N integers A1, A2, . . . , AN. [Output format] An integer represents the answer. [Sample input] 5 11 121 22 12 2023[Sample Output] 1[Example description] Delete 22, and the remaining 11, 121, 12, 2023 are the solitaire sequence. [Evaluation use case scale and convention] For 20% of the data, 1 ≤ N ≤ 20. For 50% of the data, 1 ≤ N ≤ 10000. For 100% of the data, 1 ≤ N ≤ 105, 1 ≤ Ai ≤ 109. All Ai are guaranteed not to contain leading 0s.




















Test question F: Number of islands

[Problem Description]
Xiaolan got a grid map of size M × N, which can be regarded as a grid map containing only characters
A two-dimensional array of '0' (representing seawater) and '1' (representing land). Everything outside the map can be regarded as seawater.
Each island is represented by top/bottom/left / Formed by connecting adjacent '1's in the four directions on the right.
In the grid occupied by island A, if k different grids can be selected from them, so that
their coordinates can form an arrangement like this: ( x0, y0),(x1, y1), . . . ,(xk−1, yk−1),
where (x(i+1)%k, y(i+1 )%k) is obtained by (xi, yi) moving up/down/left/right once (0 ≤ i ≤ k − 1),
At this time, these k grids are forming a "ring". If all the grids occupied by another island B are located inside the "ring"
, then we regard island B as a sub-island of island A. If B is a sub-island of A, and C is a sub-island of B, then C is also a sub-island of A. How many islands are there on this map? There is no need to count the number of sub-islands when performing statistics. [Input format] The first line contains an integer T, indicating that there are T sets of test data. Next, enter T groups of data. For each set of data, the first line contains two integers separated by spaces M and N represent the map size; then enter M lines, each line contains N characters, and the characters can only be < /span>[Sample input] For each set of data, output a line containing an integer representing the answer. [Output format] '0' or '1'.









2
5 5
01111
11001
10101 100001< /span> For 100% of the evaluation cases, 1 ≤ T ≤ 10, 1 ≤ M, N ≤ 50. For 30% of the evaluation use cases, 1 ≤ M, N ≤ 10. [Evaluation use case scale and convention] "rings" in either Island 1 or Island 2. Note that island 3 is not a child of island 1 or island 2 Island, because there are no 111111 100001 020301 111111 For the second set of data, there are three islands, distinguished below by different numbers: Island 2 is inside the "ring" of Island 1, so Island 2 is a sub-island of Island 1. The answer is 1. 100001 10001 10201 11001 01111 For the first set of data, including two islands, different The numbers are distinguished: [Example description] 3 1[Sample output] 111111 100001 010101 111111 5 6 11111
10001




























Test question G: Substring abbreviation

[Problem Description]
A very new abbreviation method is popular in the programmer circle: for a string, only the first
and the last one are retained characters, replace all characters between the first and last characters with the length of this part. For example, internation-alization is abbreviated as i18n, Kubernetes (note that the hyphen is not part of the string) is abbreviated as K8s, Lanqiao is abbreviated as L5o, etc.
In this question, we stipulate that strings with a length greater than or equal to K can use this abbreviation method
(Strings with a length less than K are not eligible to use this abbreviation. ).
Given a string S and two characters c1 and c2, please calculate how many substrings in S starting with c1
ending with c2 can use this An abbreviation?
[Input format]
The first line contains an integer K.
The second line contains a string S and two characters c1 and c2.
[Output format]
An integer represents the answer.
[Sample input]
4
abababdb a b
[Sample output]< /span> The substring that meets the conditions is as follows, and the substring is in the square brackets: < /span> |S | represents the length of string S are lowercase letters. For 100% of the data, 2 ≤ K ≤ |S | ≤ 5 × 105. S contains only lowercase letters. Both c1 and c2 For 20% of the data, 2 ≤ K ≤ |S | ≤ 10000. [Evaluation use case scale and convention] abab[abdb] ab[ababdb] ab[abab] db [abababdb] [ababab]db [abab]abdb[Example description]
6












Test question H: Integer deletion

[Problem Description]
Given an integer sequence of length N: A1, A2, . . . , AN. You need to repeat the following operation K times:
Each time, select the smallest integer in the sequence (if there is more than one minimum value, select the frontmost one), and
delete. And add the deleted value to the integer adjacent to it.
Output the sequence after K operations.
[Input format]
The first line contains two integers N and K.
The second line contains N integers, A1, A2, A3, . . . , AN.
[Output format]
Output N − K integers, separated by a space, representing the sequence after K operations.
[Sample input]
5 3
1 4 2 8 7
[Sample Example output]
17 7
[Example description]
The sequence changes as follows, the number in the brackets is the current operation The selected number in:
[1] 4 2 8 7
5 [2] 8 7
[7] 10 7
17 7
[Evaluation use case scale and convention]
For 20% of the data, 1 ≤ K < N ≤ 10000.
For 100% of the data, 1 ≤ K < N ≤ 5 × 105, 0 ≤ Ai ≤ 108.

Question I: Scenic Spot Tour Guide

[Problem Description]
There are N scenic spots in a certain scenic spot, numbered 1 to N. There are N − 1 two-way pendulum
ferry lines connecting the attractions, forming a tree-like structure. Traveling between attractions can only be done via these shuttle buses, which
will take a certain amount of time.
Xiao Ming is a senior tour guide in this scenic spot. He takes guests to visit K of them in a fixed order every day.
Attractions: A1, A2, . . . , AK . Due to time reasons today, Xiao Ming decided to skip one of the attractions and only take tourists to visit K − 1 of them in order. Specifically, if Xiao Ming chooses to skip Ai, then he will take tourists to visit A1, A2, . . . , Ai−1, Ai+1, . . . , AK, in order. (1 ≤ i ≤ K). For any Ai, please calculate how much time Xiao Ming will need to spend on the shuttle bus between the scenic spots if he skips this scenic spot? [Input format] The first line contains 2 integers N and K. The following N − 1 lines, each line contains 3 integers u, v and t, represent that there is a ferry between attractions u and v. The bus line costs t unit time. The last line contains K integers A1, A2, . . . , AK represents the original tour route. [Output format] Output K integers, where the i-th represents the time spent on the shuttle bus after skipping Ai. [Sample input] 6 4 1 2 1 1 3 1< /span> 2 6 5 1 Ai is different in every pair. For 100% of the data, 2 ≤ K ≤ N ≤ 105, 1 ≤ u, v, Ai ≤ N, 1 ≤ t ≤ 105. Guarantee For 40% of the data, 2 ≤ K ≤ N ≤ 104. For 20% of the data, 2 ≤ K ≤ N ≤ 102. [Evaluation use case scale and convention] 6 → 5 takes time 3 + 2 + 2 = 7, total time spent 14. When 1 is skipped, the route is 2 → 6 → 5, where 2 → 6 takes time 1 + 1 + 2 + 3 = 7, 6 → 1 takes time 3 + 2 + 1 = 6, the total time spent is 13. When skipping 5, the route is 2 → 6 → 1, where 2 → 6 takes time 1 + 1 + 2 + 3 = 7, 5 → 1 takes Time 2 + 1 = 3, total time spent is 7. When skipping 6, the route is 2 → 5 → 1, where 2 → 5 takes time 1 + 1 + 2 = 4, 5 → 1 takes Time 2 + 1 = 3, total time spent is 10. When skipping 2, the route is 6 → 5 → 1, where 6 → 5 takes time 3 + 2 + 2 = 7, Original route It is 2 → 6 → 5 → 1. [Sample description] 10 7 13 14[Sample output] 4 6 3 3 5 2 3 4 2



































Question J: Cutting down a tree

[Problem Description]
Given a tree composed of n nodes and m non-repeating unordered number pairs (a1, b1), (a2, b2) ,
. . . , (am, bm), where ai are different from each other, bi are different from each other, ai, bj(1 ≤ i, j ≤ m).
Xiao Ming wants to know if he can choose an edge on the tree to cut so that for each (ai
, bi) satisfies ai
is not connected to bi. If possible, output the number of the edge that should be broken (the number starts from 1 in the order of input
), otherwise output -1.
[Input format]
Input a total of n + m lines, the first line contains two positive integers n, m.
In the following n − 1 lines, each line contains two positive integers xi and yi representing the two endpoints of the i-th edge.
In the following m lines, each line contains two positive integers ai and bi.
[Output format]
One integer per line, representing the answer. If there are multiple answers, the one with the largest number will be output.
[Sample input]
6 2
1 2
2 3 After disconnecting the 4th edge, two connected blocks are formed: {1, 2, 3, 4}, {5, 6}, which also satisfy that 3 and 6 are not connected and 5 are not connected. Break After opening the second edge, two connected blocks are formed: {3, 4}, {1, 2, 5, 6}, which satisfy that 3 and 6 are not connected, and 4[Sample description] 4[Sample output] 4 5 3 6 6 5 2 5
4 3 4 is the higher number, so the answer is 4. [Evaluation use case scale and convention] For 30% of the data, it is guaranteed that 1 < n ≤ 1000. For 100% of the data, it is guaranteed that 1 < n ≤ 105, 1 ≤ m ≤ n/2.














Answer

Answer to question A:

Because it is a fill-in-the-blank question, you can write a purely violent code and run it in your own compiler.

235

Answer to question B:

We assume that 0 appears x times and 1 appears y times
We can find that the value of H(S) is equal to
Insert image description here
where x+y =n, n=23333333 in the question, so y=23333333-x,
After bringing it into the formula, traverse x from 0 to 23333333, and you can get the answer after running it in your own compiler Answer
If the answer is greater than 23333333/2, remember to update the answer to 23333333-ans, because the number of occurrences of 0 is less than the number of 1.

11027421

Answer to question C:

75 / 3 = 25
53 / 2 = 26
59 / 2 = 29
75 / (3+1) = 18
53 / (2+1) = 17
59 / (2+1) = 19

From the meaning of the question, we can know that Vmax is the minimum of all A/B
Vmin is the maximum of all A/(B+1) because it is the boundary Can't get it, so +1 is Vmin

#include <iostream>
using namespace std;

int n;
int vis;
int vis1;
int Vmin = 999999999;
int Vmax = 0;

int main()
{
    
    
    cin >> n;
    for (int i = 1; i <= n; i++)
    {
    
    
        int x, y;
        cin >> x >> y;
        int vis = x / y;
        if (vis < Vmin)
            Vmin = vis;
        vis1 = x / (y + 1) + 1;
        if (vis1 > Vmax)
            Vmax = vis1;
    }
    cout << Vmax << " " << Vmin;
    return 0;
}

Answer to question D:

Problem-solving ideas: Use full arrangement to violently measure all aircraft arrangements, and try whether it is feasible in each arrangement.

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

const int N=15;
int t[N],d[N],l[N];
int a[N];

int main()
{
    
    
	int T;
	cin>>T;
	while(T--)
	{
    
    
		int n;
		cin>>n;
		for(int i=1;i<=n;i++)
            cin>>t[i]>>d[i]>>l[i];
		for(int i=1;i<=n;i++)
			a[i]=i;
		bool flag=false;
		do
		{
    
    
			int now=0;
			for(int i=1;i<=n;i++)
			{
    
    
				if(now<=t[a[i]]+d[a[i]])
					now=l[a[i]]+max(now,t[a[i]]);
				else
					break;
				if(i==n) flag=true;
			}
			if(flag) break;
		}while(next_permutation(a+1,a+n+1));//全排列函数
		if(flag) puts("YES");
		else puts("NO");
	}
	return 0;
}

Answer to question E:

This question can be solved using linear DP
Store each number as a string, where x is the first digit and y is the last digit (for example, 114514 x= 1, y=4)
dp[y] represents the longest sequence ending with the number y
The optimal state is taken each time whether it is currently placed or not. , if you put it, the x of the current string will be the same as the previous y. The optimal state ending with y is dp[y], plus the current one is dp[x]+1

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

int n;
string s;
int dp[15];
int main()
{
    
    
   cin >> n;
   for (int i = 1; i <= n; i++)
   {
    
    
       cin >> s;
       int x = s[0] - '0';
       int y = s[s.size()-1] - '0';
       dp[y] = max(dp[y], dp[x] + 1);
   }
   int vis = 0;
   for (int i = 0; i < 10; i++)
       vis = max(vis, dp[i]);

   cout << n - vis;
   return 0;
}

Answer to question F:

Start coloring from (0,0), and color all the 0s you encounter into 2. In this way, the uncolored parts must be rings, and then search for the number of rings.

Note: When you start dyeing, there may be bevels, so you have to use eight-way search; when searching for rings, use four-way search.

#include<bits/stdc++.h>
using namespace std;
#define ll long long
const int N = 5e1 + 5;
int T, m, n;
char g[N][N];
int dx[8] = {
    
    0, 0, 1, -1, 1, 1, -1, -1};
int dy[8] = {
    
    1, -1, 0, 0, -1, 1, 1, -1};
int ans;
struct point {
    
    
    int x, y;
};
void bfs1() {
    
    
    queue<point>q;
    g[0][0] = '2';
    q.push({
    
    0, 0});
    while (!q.empty()) {
    
    
        point now = q.front();
        q.pop();
        for (int i = 0; i < 8; i++) {
    
    
            int tx = now.x + dx[i];
            int ty = now.y + dy[i];
            if (tx >= 0 && ty >= 0 && tx <= m + 1 && ty <= n + 1) {
    
    
                if (g[tx][ty] == '0') {
    
    
                    g[tx][ty] = '2';
                    q.push({
    
    tx, ty});
                }
            }
        }
    }
}
void bfs2(int x, int y) {
    
    
    queue<point>q;
    g[x][y] = '2';
    q.push({
    
    x, y});
    while (!q.empty()) {
    
    
        point now = q.front();
        q.pop();
        for (int i = 0; i < 4; i++) {
    
    
            int tx = now.x + dx[i];
            int ty = now.y + dy[i];
            if (tx >= 1 && ty >= 1 && tx <= m && ty <= n) {
    
    
                if (g[tx][ty] == '0' || g[tx][ty] == '1') {
    
    
                    g[tx][ty] = '2';
                    q.push({
    
    tx, ty});
                }
            }
        }
    }
}
int main() {
    
    
    cin >> T;
    while (T--) {
    
    
        cin >> m >> n;
        memset(g, '0', sizeof(g));
        ans = 0;
        for (int i = 1; i <= m; i++) {
    
    
            for (int j = 1; j <= n; j++) {
    
    
                cin >> g[i][j];
            }
        }
        bfs1();
        for (int i = 1; i <= m; i++) {
    
    
            for (int j = 1; j <= n; j++) {
    
    
                if (g[i][j] == '1') {
    
    
                    ans++;
                    bfs2(i, j);
                }
            }
        }
        cout << ans << endl;
    }
    return 0;
}

Answer to question G:

This problem can also be solved using DP
We treat the string from back to front, and define dp[i] to mean that the string is from i to the end of the string len, which is [ i , len] The number of c2 in the interval
State transition equation:
Insert image description here
ans is all when in the interval [1, len-k+1] >s[i]=c1 The sum of f[ i+k-1 ]
That is, when s[i] = c1 When, ans+= f[ i+k-1 ] (the number of c2 in the interval from i+k-1 to len)

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

const int N = 5e5 + 5;
int k;
string s;
char c1, c2;
int f[N];
ll ans;

int main() {
    
    
    cin >> k >> s >> c1 >> c2;
    int len = s.size();
    s = " " + s;
    for (int i = len; i >= 1; i--) {
    
    
        f[i] = f[i + 1];
        if (s[i] == c2) f[i] = f[i + 1] + 1;
    }
    for (int i = 1; i + k - 1 <= len; i++) {
    
    
        if (s[i] == c1) ans += f[i + k - 1];
    }
    cout << ans;
    return 0;
}

Answer to question H:

Since a large number of deletion operations are required, it is not difficult to think of using a linked list.

This question requires dynamically finding the minimum value, so obviously a heap can be used.

Each time, the subscript of the minimum value is taken from the heap and then deleted from the linked list.

But the special point of this question isdelete it. And add the deleted value to the integer adjacent to it, so the weight of the elements still in the heap will change.

We can notice that each deletion operation will only make some elements larger, but not smaller. In other words, the original minimum value may become something other than the minimum value.

Therefore, when we take out the minimum value in the heap, we need to compare the sorting weight of this element with the actual value. If the actual value becomes larger, the current element is not necessarily the minimum value and needs to be put back into the heap.

#include <bits/stdc++.h>
using namespace std;
using ll = long long;
const int N = 5e5 + 10;
ll v[N], l[N], r[N];
//双向链表的删除操作, 删除x结点
void del(int x) {
    
    
    r[l[x]] = r[x], l[r[x]] = l[x];
    v[l[x]] += v[x], v[r[x]] += v[x];
}
int main () {
    
    
    int n, k; cin >> n >> k;
    //最小堆, 堆中的元素是{权值, 结点下标}
    priority_queue<pair<ll, int>, vector<pair<ll, int>>, greater<pair<ll, int>>> h;
    //输入并构造双向链表
    r[0] = 1, l[n + 1] = n;
    for (int i = 1; i <= n; i ++)
        cin >> v[i], l[i] = i - 1, r[i] = i + 1, h.push({
    
    v[i], i});
    while (k --) {
    
    
        auto p = h.top(); h.pop();
        //如果v发生变化, 则目前的元素不一定是最小值, 需要重新放入堆中
        if (p.first != v[p.second]) h.push({
    
    v[p.second], p.second}), k ++;
        else del(p.second);
    }
    //输出链表剩余的元素
    int head = r[0];
    while (head != n + 1) {
    
    
        cout << v[head]<< " ";
        head = r[head];
    }
    return 0;
}

Answer to question I:

One thing to be sure of is that since the graph in the question is a tree, for any two vertices, their shortest path is their simple path.

To find the simple path distance between two nodes in the tree, you can think of using their nearest common ancestor, which is LCA.
This question is a template question for LCA. You can use the doubling method or the tarjan algorithm.
The distance may exceed int, so it is recommended to use long long for all integers.

#include <bits/stdc++.h>
using namespace std;
const int N = 1e5 + 10;
using ll = long long;
vector<pair<int, int>> g[N];
ll dep[N], f[N][30], dist[N];
//倍增LCA预处理
void dfs(int u, int fa, ll d) {
    
    
    dep[u] = dep[fa] + 1, dist[u] = d, f[u][0] = fa;
    for (int i = 1; (1 << i) <= dep[u]; i ++) f[u][i] = f[f[u][i - 1]][i - 1];
    for (auto &p : g[u]) {
    
    
        if (p.first == fa) continue;
        dfs(p.first, u, d + p.second);
    }
}
//求a和b的lca
int lca(int a, int b) {
    
    
    if (dep[a] < dep[b]) swap(a, b);
    for (int i = 20; i >= 0; i --) {
    
    
        if (dep[f[a][i]] >= dep[b]) a = f[a][i];
        if (a == b) return a;
    }
    for (int i = 20; i >= 0; i --) {
    
    
        if (f[a][i] != f[b][i]) a = f[a][i], b = f[b][i];
    }
    return f[a][0];
}
ll get(int a, int b) {
    
    
    return dist[a] + dist[b] - 2 * dist[lca(a, b)];
}
int main () {
    
    
    int n, k; cin >> n >> k;
    for (int i = 1; i < n; i ++) {
    
    
        int u, v, t; cin >> u >> v >> t;
        g[u].push_back({
    
    v, t}), g[v].push_back({
    
    u, t});
    }
    vector<int> a(k);
    for (auto &x : a) cin >> x;
    dfs(1, 0, 0);
    //求出原本整条路径的和
    ll sum = 0;
    for (int i = 1; i < k; i ++) sum += get(a[i - 1], a[i]);
    //依次求出删除每个点时的和
    for (int i = 0; i < k; i ++) {
    
    
        ll ans = sum;
        //减去当前顶点和左右顶点的路径距离
        if (i != 0) ans -= get(a[i], a[i - 1]);
        if (i != k - 1) ans -= get(a[i], a[i + 1]);
        //左右都有顶点时, 要把两个顶点接到一起
        if (i != 0 && i != k - 1) ans += get(a[i - 1], a[i + 1]);
        cout << ans << " ";
    }
    return 0;
}

Answer to question J:

#include <bits/stdc++.h>
using namespace std;
const int N = 1e5 + 10, M = 18;
vector<pair<int, int>> g[N];
int dep[N], f[N][20], cnt[N], w[N];
void init(int u, int fa) {
    
    
  dep[u] = dep[fa] + 1, f[u][0] = fa;
  for (int i = 1; (1 << i) <= dep[u]; i ++) f[u][i] = f[f[u][i - 1]][i - 1];
  for (auto &e : g[u]) {
    
    
    if (e.first != fa) init(e.first, u), w[e.first] = e.second;
  }
}
int lca(int a, int b) {
    
    
  if (dep[a] < dep[b]) swap(a, b);
  for (int i = M; i >= 0; i --) {
    
    
    if (dep[f[a][i]] >= dep[b]) a = f[a][i];
    if (a == b) return a;
  }
  for (int i = M; i >= 0; i --) {
    
    
    if (f[a][i] != f[b][i]) a = f[a][i], b = f[b][i];
  }
  return f[a][0];
}
void add(int a, int b) {
    
    
  int LCA = lca(a, b);
  cnt[a] ++, cnt[b] ++, cnt[LCA] -= 2;
}
void dfs(int u, int fa) {
    
    
  for (auto &e : g[u]) {
    
    
    if (e.first != fa) 
      dfs(e.first, u), cnt[u] += cnt[e.first];
  }
}
int main () {
    
    
  int n, m; cin >> n >> m;
  for (int i = 1; i < n; i ++) {
    
    
    int a, b; cin >> a >> b;
    g[a].push_back({
    
    b, i}), g[b].push_back({
    
    a, i});
  }
  init(1, 0);
  for (int i = 0; i < m; i ++) {
    
    
    int a, b; cin >> a >> b;
    add(a, b);
  }
  dfs(1, 0);
  int res = -1;
  for (int i = 1; i <= n; i ++) 
    if (cnt[i] == m && (w[i] > res)) res = w[i];
  cout << res << endl;
  return 0;
}

Guess you like

Origin blog.csdn.net/Stephen_Curry___/article/details/132473425