← Home
```go
package main

import (
	"bufio"
	"io"
	"os"
	"strconv"
)

func main() {
	data, _ := io.ReadAll(os.Stdin)
	idx := 0
	nextInt := func() int {
		for idx < len(data) && (data[idx] < '0' || data[idx] > '9') && data[idx] != '-' {
			idx++
		}
		sign := 1
		if idx < len(data) && data[idx] == '-' {
			sign = -1
			idx++
		}
		val := 0
		for idx < len(data) && data[idx] >= '0' && data[idx] <= '9' {
			val = val*10 + int(data[idx]-'0')
			idx++
		}
		return sign * val
	}

	n := nextInt()
	c := make([]int64, n+1)
	for i := 1; i <= n; i++ {
		c[i] = int64(nextInt())
	}

	m := n - 1
	head := make([]int, n+1)
	to := make([]int, 2*m+5)
	nxt := make([]int, 2*m+5)
	ec := 0
	addEdge := func(u, v int) {
		ec++
		to[ec] = v
		nxt[ec] = head[u]
		head[u] = ec
	}

	for i := 0; i < m; i++ {
		u := nextInt()
		v := nextInt()
		addEdge(u, v)
		addEdge(v, u)
	}

	parent := make([]int, n+1)
	childCnt := make([]int, n+1)
	order := make([]int, 0, n)
	stack := make([]int, 0, n)
	stack = append(stack, 1)
	parent[1] = 0

	for len(stack) > 0 {
		v := stack[len(stack)-1]
		stack = stack[:len(stack)-1]
		order = append(order, v)
		for e := head[v]; e != 0; e = nxt[e] {
			u := to[e]
			if u == parent[v] {
				continue
			}
			parent[u] = v
			childCnt[v]++
			stack = append(stack, u)
		}
	}

	A := make([]int64, n+1)
	B := make([]int64, n+1)
	sumA := make([]int64, n+1)
	minDiff := make([]int64, n+1)
	cntMin := make([]int, n+1)

	const INF int64 = 1 << 60

	for i := n - 1; i >= 0; i-- {
		v := order[i]
		if childCnt[v] == 0 {
			A[v] = c[v]
			B[v] = 0
			continue
		}
		s := int64(0)
		md := INF
		cnt := 0
		for e := head[v]; e != 0; e = nxt[e] {
			u := to[e]
			if u == parent[v] {
				continue
			}
			s += A[u]
			d := B[u] - A[u]
			if d < md {
				md = d
				cnt = 1
			} else if d == md {
				cnt++
			}
		}
		sumA[v] = s
		minDiff[v] = md
		cntMin[v] = cnt
		B[v] = s + md
		A[v] = s
		if t := c[v] + B[v]; t < A[v] {
			A[v] = t
		}
	}

	reachA := make([]bool, n+1)
	reachB := make([]bool, n+1)
	reachA[1] = true

	for _, v := range order {
		if childCnt[v] == 0 {
			continue
		}
		opt0 := reachA[v] && sumA[v] == A[v]
		opt1 := reachA[v] && c[v]+B[v] == A[v]
		rb := reachB[v]
		if !opt0 && !opt1 && !rb {
			continue
		}
		md := minDiff[v]
		cnt := cntMin[v]
		for e := head[v]; e != 0; e = nxt[e] {
			u := to[e]
			if u == parent[v] {
				continue
			}
			d := B[u] - A[u]
			if opt0 {
				reachA[u] = true
			}
			if opt1 || rb {
				if d == md {
					reachB[u] = true
				}
				if d > md || cnt >= 2 {
					reachA[u] = true
				}
			}
		}
	}

	ans := make([]bool, n+1)
	k := 0
	for v := 1; v <= n; v++ {
		ok := false
		if c[v] == 0 {
			ok = true
		} else if childCnt[v] == 0 {
			if reachA[v] {
				ok = true
			}
		} else {
			if reachA[v] && c[v]+B[v] == A[v] {
				ok = true
			}
		}
		ans[v] = ok
		if ok {
			k++
		}
	}

	out := make([]byte, 0, n*8+64)
	out = strconv.AppendInt(out, A[1], 10)
	out = append(out, ' ')
	out = strconv.AppendInt(out, int64(k), 10)
	out = append(out, '\n')
	first := true
	for i := 1; i <= n; i++ {
		if ans[i] {
			if !first {
				out = append(out, ' ')
			}
			first = false
			out = strconv.AppendInt(out, int64(i), 10)
		}
	}
	out = append(out, '\n')

	w := bufio.NewWriterSize(os.Stdout, 1<<20)
	w.Write(out)
	w.Flush()
}
```