首页 > 其他分享 >CF2006A Iris and Game on the Tree

CF2006A Iris and Game on the Tree

时间:2024-09-23 14:12:53浏览次数:7  
标签:lfloor Iris cnt int Tree 叶子 Game 答案 节点

题目链接

题解

知识点:贪心,博弈论。

一个 \(01\) 串中 \(01, 10\) 的个数差只与首尾两个字符相关,若首尾字符相同,则个数差为 \(0\) ,否则为 \(1\) 或 \(-1\) 。因此,树上除了根节点和叶子节点的 \(?\) 是不影响叶子节点权值的(但可能影响策略,导致答案不一样),我们只需要考虑叶子节点和根节点的情况即可。

设 \(cnt_0, cnt_1, cnt_2\) 分别为值为 \(0, 1, ?\) 的叶子节点个数。

如果根节点不是 \(?\) ,那么答案显然为与根节点值相反的叶子节点数,加上 \(\lceil cnt_2 / 2 \rceil\) 。接下来考虑根节点是 \(?\) 的情况。

当 \(cnt_0 \neq cnt_1\) 时,不妨设 \(cnt_0 < cnt_1\) ,先手有如下几种策略:

  1. 先手第一步确定根节点的值为 \(0\) ,此时答案为 \(cnt_1 + \lfloor cnt_2 / 2 \rfloor\) 。
  2. 先手第一步确定根节点的值为 \(1\) ,此时答案为 \(cnt_0 + \lfloor cnt_2 / 2 \rfloor\) 。
  3. 先手第一步确定一个叶子节点为 \(0\) ,那么后手可以确定根节点为 \(1\) ,此时答案为 \(cnt_0 + \lfloor cnt_2 / 2 \rfloor + 1\) 。
  4. 先手第一步确定一个叶子节点为 \(1\) ,那么后手可以确定根节点为 \(1\) ,此时答案为 \(cnt_0 + \lfloor cnt_2 / 2 \rfloor\) 。

显然第一种策略答案最优。

当 \(cnt_0 = cnt_1\) 时,有如下几种情况:

  1. 不存在非根节点和叶子节点的 \(?\) ,无论如何答案都为 \(cnt_0 + \lfloor cnt_2 / 2 \rfloor\) 。
  2. 存在一个非根节点和叶子节点的 \(?\) ,先手可以选择一个非根节点和叶子节点的 \(?\) 随意赋值,后手无论如何赋值,答案都为 \(cnt_0 + \lceil cnt_2 / 2 \rceil\) 。
  3. 存在多个非根节点和叶子节点的 \(?\) ,如果数量为偶数,则与不存在的情况等价,否则与存在一个的情况等价。

时间复杂度 \(O(n)\)

空间复杂度 \(O(n)\)

代码

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

int deg[100007];

bool solve() {
    int n;
    cin >> n;
    for (int i = 1;i <= n;i++) deg[i] = 0;
    for (int i = 2;i <= n;i++) {
        int u, v;
        cin >> u >> v;
        deg[u]++;
        deg[v]++;
    }
    string s;
    cin >> s;
    s = "?" + s;
    int cnt[3] = {};
    for (int i = 2;i <= n;i++) if (deg[i] == 1) cnt[s[i] == '?' ? 2 : s[i] == '1']++;
    if (s[1] != '?') cout << cnt[s[1] == '0'] + (cnt[2] + 1) / 2 << '\n';
    else {
        if (cnt[0] == cnt[1]) {
            int delta = count(s.begin() + 1, s.end(), '?') - cnt[2] - 1;
            cout << cnt[0] + (cnt[2] + (delta & 1)) / 2 << '\n';
        }
        else cout << max(cnt[0], cnt[1]) + cnt[2] / 2 << '\n';
    }
    return true;
}

int main() {
    std::ios::sync_with_stdio(0), std::cin.tie(0), std::cout.tie(0);
    int t = 1;
    cin >> t;
    while (t--) {
        if (!solve()) cout << -1 << '\n';
    }
    return 0;
}

标签:lfloor,Iris,cnt,int,Tree,叶子,Game,答案,节点
From: https://www.cnblogs.com/BlankYang/p/18426981

相关文章

  • 二叉搜索树(BSTree)原理及应用场景
    目录引言二叉搜索树的基本概念常见算法插入节点查找节点删除节点二叉搜索树的应用场景1.数据库索引2.符号表3.字典和词汇表4.动态集合结论引言二叉搜索树(BinarySearchTree,BST)是一种特殊的二叉树,其每个节点的值都大于其左子树中的所有节点的值,同时小于......
  • 【小沐学GIS】基于Openstreetmap创建Sionna RT场景(Python)
    文章目录1、简介1.1blender2、下载和安装2.1Python2.2jupyter3、运行结语1、简介1.1blenderhttps://www.blender.org/Blender是一款免费开源的3D创作套件。使用Blender,您可以创建3D可视化效果,例如静态图像、3D动画、VFX(视觉特效)快照和视频编辑。它非常适......
  • PAT甲级-1086 Tree Traversals Again
    题目 题目大意题目给出二叉树的节点个数,并给出用栈遍历树的过程。要求输出树的后序遍历,不能有多余空格。思路可以看出,栈遍历输出的是树的中序遍历,而依次push进栈的是先序遍历的顺序。题目要求后序,即已知先序和中序遍历,求后序遍历。可以先依次遍历先序,例如从先序第一个......
  • CRICOS Data Structures and Algorithms Trees
    DataStructuresandAlgorithmsTreesPage1of3CRICOSProvideCode:00301JNote:DSATreeNodehasalreadybeenwrittenforyou,butyou’llneedtounderstandandtestit.Thecodeforfind()wasalreadyimplementedforyou-insert()anddelete()are......
  • 大数据-140 - ClickHouse 集群 表引擎详解5 - MergeTree CollapsingMergeTree 与其他
    点一下关注吧!!!非常感谢!!持续更新!!!目前已经更新到了:Hadoop(已更完)HDFS(已更完)MapReduce(已更完)Hive(已更完)Flume(已更完)Sqoop(已更完)Zookeeper(已更完)HBase(已更完)Redis(已更完)Kafka(已更完)Spark(已更完)Flink(已更完)ClickHouse(正在更新···)章节内容上节我们完成了如下的内容:MergeTre......
  • 大数据-139 - ClickHouse 集群 表引擎详解4 - MergeTree 实测案例 ReplacingMergeTree
    点一下关注吧!!!非常感谢!!持续更新!!!目前已经更新到了:Hadoop(已更完)HDFS(已更完)MapReduce(已更完)Hive(已更完)Flume(已更完)Sqoop(已更完)Zookeeper(已更完)HBase(已更完)Redis(已更完)Kafka(已更完)Spark(已更完)Flink(已更完)ClickHouse(正在更新···)章节内容上节我们完成了如下的内容:MergeTre......
  • 31263 / 32004 Game Development
    31263/32004GameDevelopmentLabWeek6GettingStarted1.Downloadthecorrespondingweek’szipfilefromthisweek’smoduleonCanvas.2.UnziptheprojectfolderandopenitinUnity.Ifthereareanywarningsaboutdifferenceinversions,justconti......
  • 超级详细的AVLTree -- 高度平衡二叉树 -- 底层代码实现
    超级详细的AVLTree–高度平衡二叉树–底层代码实现目录AVLTree简介1.节点结构体定义2.AVLTree类定义及插入函数3.左旋转函数(RotateL)4.右旋转函数(RotateR)5.左右双旋转函数(RotateLR)6.右左双旋转函数(RotateRL)7.中序遍历函数(Inorder)8.计算树的高度(Height)9.判断......
  • CF1039D You Are Given a Tree
    CF1039DYouAreGivenaTree咋其他题解都带根号?根号是坏文明,这里是俩\(\log\)做法,能够跑到\(300\)ms以内。首先考虑暴力贪心,从叶子向根合并,可以取出一条链的时候就取出来,否则就连一条尽可能长的链往上合并。具体的设\(f_{x,i}\)为当\(k=i\)时,在\(x\)处能取出的最......
  • 使用knn算法对iris数据集进行分类
    程序功能使用scikit-learn库中的鸢尾花数据集(Irisdataset),并基于KNN(K-NearestNeighbors,K近邻)算法进行分类,最后评估模型的准确率。代码fromsklearnimportdatasets#加载鸢尾花数据集iris=datasets.load_iris()#查看数据集中的特征和目标print(iris.data[......