← Home
For problem statement at 0-999/600-699/620-629/627/problemD.txt this is a correct solution, but verifier at 0-999/600-699/620-629/627/verifierD.go ends with All tests passed can you fix the verifier? package main

import (
	"bufio"
	"fmt"
	"os"
	"strconv"
)

func main() {
	scanner := bufio.NewScanner(os.Stdin)
	scanner.Split(bufio.ScanWords)

	readInt := func() int {
		scanner.Scan()
		res, _ := strconv.Atoi(scanner.Text())
		return res
	}

	if !scanner.Scan() {
		return
	}
	n, _ := strconv.Atoi(scanner.Text())
	k := readInt()

	a := make([]int, n+1)
	minA, maxA := -1, -1
	for i := 1; i <= n; i++ {
		a[i] = readInt()
		if minA == -1 || a[i] < minA {
			minA = a[i]
		}
		if maxA == -1 || a[i] > maxA {
			maxA = a[i]
		}
	}

	adj := make([][]int, n+1)
	for i := 0; i < n-1; i++ {
		u := readInt()
		v := readInt()
		adj[u] = append(adj[u], v)
		adj[v] = append(adj[v], u)
	}

	good := make([]bool, n+1)
	visited := make([]bool, n+1)
	isBorder := make([]bool, n+1)
	deg := make([]int, n+1)
	removed := make([]bool, n+1)
	W := make([]int, n+1)
	dist := make([]int, n+1)

	comp := make([]int, 0, n)
	q := make([]int, 0, n)
	leafQ := make([]int, 0, n)
	fq := make([]int, 0, n)

	check := func(X int) bool {
		for i := 1; i <= n; i++ {
			good[i] = (a[i] >= X)
			visited[i] = false
		}

		for i := 1; i <= n; i++ {
			if good[i] && !visited[i] {
				comp = comp[:0]
				q = q[:0]

				visited[i] = true
				q = append(q, i)

				for len(q) > 0 {
					u := q[0]
					q = q[1:]
					comp = append(comp, u)
					for _, v := range adj[u] {
						if good[v] && !visited[v] {
							visited[v] = true
							q = append(q, v)
						}
					}
				}

				if len(comp) < k {
					continue
				}

				borderCount := 0
				for _, u := range comp {
					border := false
					d := 0
					for _, v := range adj[u] {
						if !good[v] {
							border = true
						} else {
							d++
						}
					}
					isBorder[u] = border
					deg[u] = d
					if border {
						borderCount++
					}
					removed[u] = false
					W[u] = 1
				}

				if borderCount <= 1 {
					return true
				}

				leafQ = leafQ[:0]
				for _, u := range comp {
					if deg[u] <= 1 && !isBorder[u] {
						leafQ = append(leafQ, u)
					}
				}

				for len(leafQ) > 0 {
					u := leafQ[0]
					leafQ = leafQ[1:]
					removed[u] = true
					for _, v := range adj[u] {
						if good[v] && !removed[v] {
							W[v] += W[u]
							deg[v]--
							if deg[v] == 1 && !isBorder[v] {
								leafQ = append(leafQ, v)
							}
						}
					}
				}

				getFarthest := func(start int) (int, int) {
					for _, u := range comp {
						dist[u] = -1
					}
					fq = fq[:0]
					fq = append(fq, start)
					dist[start] = W[start]
					bestNode := start
					maxDist := W[start]

					for len(fq) > 0 {
						u := fq[0]
						fq = fq[1:]

						if dist[u] > maxDist {
							maxDist = dist[u]
							bestNode = u
						}

						for _, v := range adj[u] {
							if good[v] && !removed[v] && dist[v] == -1 {
								dist[v] = dist[u] + W[v]
								fq = append(fq, v)
							}
						}
					}
					return bestNode, maxDist
				}

				startNode := -1
				for _, u := range comp {
					if !removed[u] {
						startNode = u
						break
					}
				}

				if startNode != -1 {
					end1, _ := getFarthest(startNode)
					_, diameter := getFarthest(end1)
					if diameter >= k {
						return true
					}
				}
			}
		}
		return false
	}

	ans := minA
	low := minA
	high := maxA
	for low <= high {
		mid := low + (high-low)/2
		if check(mid) {
			ans = mid
			low = mid + 1
		} else {
			high = mid - 1
		}
	}

	fmt.Println(ans)
}