首页 > 其他分享 >CF1777D题解

CF1777D题解

时间:2023-10-25 10:04:20浏览次数:37  
标签:frac int 题解 频率 res CF1777D 变成 节点

  • 分析

    首先看到那个 \(10^{100}\) 再加上样例,我们就能意识到在不是特别多的操作次数后这颗树上的值就会全变成 \(0\)。
    因为没有子节点在一次操作后显然就会变成 \(0\),然后第一次叶节点就会变成 \(0\),然后下一次子节点中只有叶节点的就会变成 \(0\),以此类推,理论上最多操作 \(n\) 次一棵树就会全变成 \(0\)。
    定义一个点的子树内全为 \(0\) 时为该点彻底变成 \(0\)。
    所以问题变成了对于初值的所有情况,求出所有点在彻底变成 \(0\) 前值为 \(1\) 的次数和。

    思考如何计算次数,显然初值共有 \(2^{n}\) 种情况,对于每种情况分别计算是非常低效的。
    所有我们可以对于所有情况一起计算,那么这时我们求的就是每次操作后单点的值为 \(1\) 的情况的频数 \(=\) 频率 \(\times\) 总情况数。
    可以发现对于单点而言,它的初始值为 \(1\) 的频率是 \(\frac{1}{2}\)。

    考虑推广到初始后到彻底变成 \(0\) 前的状态,那么加入子节点的异或,假设所有子节点是叶节点,那么对于单个子节点,\(1\) 的频率为 \(\frac{1}{2}\),再加入一个子节点,发现原来 \(0\) 和 \(1\) 的频率互换了,但是由于两者相等,都是 \(\frac{1}{2}\),所以频率保持不变,易发现对于子节点全为叶节点的节点频率也为 \(\frac{1}{2}\),那么一步步往根节点推,再算上初始状态,可以发现所有节点在彻底变成 \(0\) 之前,每次操作后为 \(1\) 的频率都为 \(\frac{1}{2}\)。

    那么现在的问题是如何求出彻底变成 \(0\) 所需的次数,注意到彻底变成 \(0\) 前需要一个点的子树内(除了该点)全变成 \(0\),否则因为是从下向上一步步变的,会存在至少一个最高的点,即该点的子节点没有彻底变成 \(0\),那么在下一次该点仍能通过此子节点转移,频率仍为 \(\frac{1}{2}\),所以需要子树全变成 \(0\)。
    因为是从下往上一步步变的,所以一个子树全变成 \(0\) 的次数为最长链的长度。算上初状态频率为 \(\frac{1}{2}\) 的次数为最长链长度 \(+1\)。

    总情况数为 \(2^{n}\),那么答案为\(\sum_{i=1}^{n}(子树内最长链长度 + 1) \times \frac{1}{2} \times 2^{n} = \sum_{i=1}^{n}(子树内最长链长度 + 1) \times 2^{n - 1}\)。

  • 代码

#include <iostream>
#include <vector>
#define int long long
using namespace std;
constexpr int MAXN(1000007);
constexpr int mod(1000000007);
vector <int> e[MAXN];
int cl[MAXN];
int T, n, ans;
inline void read(int &temp) { cin >> temp; }
inline int ksm(int base, int k) {
	int res(1);
	while (k) {
		if (k & 1)  res = res * base % mod;
		base = base * base % mod, k >>= 1;
	}
	return res;
}
void dfs(int u, int fa) {
	int res(0);
	for (auto v : e[u]) {
		if (v == fa)  continue;
		dfs(v, u);
		res = max(res, cl[v]);
	}
	cl[u] = res + 1;
}
inline void work() {
	for (int i(1); i <= n; ++i)  e[i].clear();
	ans = 0;
	read(n);
	for (int i(1), u, v; i < n; ++i)  read(u), read(v), e[u].push_back(v), e[v].push_back(u);
	dfs(1, 0);
	for (int i(1); i <= n; ++i)  ans = (ans + cl[i]) % mod;
	ans = ans * ksm(2, n - 1) % mod;
	cout << ans << endl;
}
signed main() {
	ios::sync_with_stdio(false), cin.tie(nullptr), cout.tie(nullptr);
	read(T);
	while (T--)  work(); 
	return 0;
}

标签:frac,int,题解,频率,res,CF1777D,变成,节点
From: https://www.cnblogs.com/Kazdale/p/17786412.html

相关文章

  • CF1878B题解
    CF1878BAleksaandStack题目翻译给定\(n\),试构造一个长度为\(n\)的严格上升正整数序列\(a_1,a_2,a_3,...,a_n\)使得\(\foralli\in[3,n],(a_{i-1}+a_{i-2})\nmid3a_i\)。单个测试点内包含多组测试数据。思路拿到题目,发现不好一个数一个数地构造,考虑......
  • 华科新生赛题解
    因为学校里面写代码的条件不足,比如教学楼里面使用键盘就会被盯着看。感觉有点点自闭。早知道退学了。不知道现在退学是不是算晚。昨天好兄弟车昱辉说你是在学习又不是在打游戏,但是我还是很羞涩。Abfs,需要把已经搜到的点在枚举1到n的时候去掉,所以可以使用并查集。或者链表......
  • CF1777C题解
    分析看到题面里面的子序列觉得很恶心,如果是子段感觉就会比较好做。如果直接填上子序列中间的空隙就可能会取一些比必须要取的数更大或者更小的数,影响我们的答案。那么就可以直接排序,使得子序列中间的空隙的数必然\(\geq\)左端且\(\leq\)右端,不会影响我们的答案(因为极差只......
  • [题解]CF1223F Stack Exterminable Arrays
    CCF出的原题观摩一下。思路首先可以用一个Trie来维护。在这里对本文中的一些变量做一下说明。\(p\)表示当前维护的Trie中,指向的元素编号。\(t_i\)表示在Trie中编号为\(i\)的元素在原序列中的值。\(f_i\)表示在Trie中编号为\(i\)的元素在Trie中的父......
  • CSP-S 2023 题解
    CSP-S2023题解游记打得非常烂。。。也是一个经验的总结吧:T1.密码锁(lock)似乎也没什么好讲的,直接模拟枚举每一种情况即可。放上我的考场代码。#include<bits/stdc++.h>usingnamespacestd;intn,a[10][8],b[2][90][8],ans=0,len,l;intread(){intx=0,f=1;char......
  • Codeforces 1862G 题解
    传送门题解因为有这个操作:将序列\(a\)加上\(\{n,n-1,\cdots,1\}\),考虑差分。那么显然每次操作会将差分数组中的每个元素减去\(1\),如果差分数组中有\(0\),就会把\(0\)删除。所以可以发现差分数组中剩下的一定是操作前的最大值。由于操作后最大值还是最大值,最小值仍......
  • CF1777A题解
    分析发现操作2不会改变数的奇偶性,故无视。那么操作就是单纯删一个数。对于一个连续出现\(x\)个奇偶性相同的数的序列,需要删\(x-1\)个数(因为只剩下一个数就不会和相邻的数奇偶性相同了)。觉得找序列太麻烦,观察到连续出现\(x\)个奇偶性相同的数的序列有\(x-1\)个不......
  • CF1523D Love-Hate 题解
    抽象化题意:一共有\(m\)个元素,给定\(n\)个集合,每个集合的元素不超过\(15\)个,求出一个元素个数最多的集合\(S\)是至少\(\lceil\dfrac{n}{2}\rceil\)个集合的子集。其中$p$$(1\len\le2\cdot10^5,1\lep\lem\le60)$我们先假设\(limit=\lceil\dfrac......
  • 2023级HAUT新生周赛题解汇总
    2023级HAUT新生周赛(零)熟悉周赛规则专场:2023级HAUT新生周赛(一)@21级学长专场(张子豪,张鑫,李昊阳):2023级HAUT新生周赛(二)@曹瑞峰专场:2023级HAUT新生周赛(三)@22级学姐专场(杨焱,刘振歌,周欣滢):2023级HAUT新生周赛(四)@牛浩然专场:2023级HAUT新生周赛(五)@陈兰锴专场:......
  • JWT Tool:针对 JSON Web Tokens 的测试工具题解JWT cracking
    什么是JWT?JWT是JSONWebToken的缩写,它是一串带有声明信息的字符串,由服务端使用加密算法对信息签名,以保证其完整性和不可伪造性。Token里可以包含所有必要的信息,这样服务端就无需保存任何关于用户或会话的信息了。JWT可用于身份认证,会话状态维持以及信息交换等任务。JWT由三部分......