2920. 收集所有金币可获得的最大积分

2920. 收集所有金币可获得的最大积分


题目链接:2920. 收集所有金币可获得的最大积分

代码如下:

//参考链接:https://leetcode.cn/problems/maximum-points-after-collecting-coins-from-all-nodes/solutions/2503152/shu-xing-dp-ji-yi-hua-sou-suo-by-endless-phzx
class Solution {
public:
	int maximumPoints(vector<vector<int>>& edges, vector<int>& coins, int k) {
		vector<vector<int>> g(coins.size());
		for (auto& edge : edges) {
			int x = edge[0], y = edge[1];
			g[x].push_back(y);
			g[y].push_back(x);
		}

		array<int, 14> init_val;
		ranges::fill(init_val, -1); // -1 表示没有计算过
		vector memo(coins.size(), init_val);
		auto dfs = [&](auto&& dfs, int i, int j, int fa) {
			int& res = memo[i][j];
			if (res != -1) {//之前计算过
				return res;
			}
			int res1 = (coins[i] >> j) - k;
			int res2 = coins[i] >> (j + 1);
			for (int ch : g[i]) {
				if (ch == fa) { continue; }
				res1 += dfs(dfs, ch, j, i);// 不右移
				if (j < 13) {// j+1 >= 14 相当于 res2 += 0,无需递归
					res2 += dfs(dfs, ch, j + 1, i);// 右移
				}
			}
			return res = max(res1, res2);//记忆化
			};
		return dfs(dfs, 0, 0, -1);
	}
};

你可能感兴趣的:(leetcode,c++)