4 - 09. 笛卡尔树(25)
来源:互联网 发布:spsss软件如何安装 编辑:程序博客网 时间:2024/04/29 15:17
4 - 09. 笛卡尔树(25)题目地址
时间限制
400 ms
内存限制
65536 kB
代码长度限制
8000 B
判题程序
Standard
笛卡尔树是一种特殊的二叉树,其结点包含两个关键字K1和K2。首先笛卡尔树是关于K1的二叉搜索树,即结点左子树的所有K1值都比该结点的K1值小,右子树则大。其次所有结点的K2关键字满足优先队列(不妨设为最小堆)的顺序要求,即该结点的K2值比其子树中所有结点的K2值小。给定一棵二叉树,请判断该树是否笛卡尔树。
输入格式说明:
输入首先给出正整数N(<=1000),为树中结点的个数。随后N行,每行给出一个结点的信息,包括:结点的K1值、K2值、左孩子结点编号、右孩子结点编号。设结点从0~(N-1)顺序编号。若某结点不存在孩子结点,则该位置给出-1。
输出格式说明:
输出YES如果该树是一棵笛卡尔树;否则输出NO。
样例输入与输出:
序号 输入 输出
1
6
8 27 5 1
9 40 -1 -1
10 20 0 3
12 21 -1 4
15 22 -1 -1
5 35 -1 -1
YES
2
6
8 27 5 1
9 40 -1 -1
10 20 0 3
12 11 -1 4
15 22 -1 -1
50 35 -1 -1
NO
3
7
8 27 5 1
9 40 -1 -1
10 20 0 3
12 22 -1 4
15 21 6 -1
5 35 -1 -1
13 23 -1 -1
NO
4
6
8 27 5 1
9 40 -1 -1
10 20 0 3
12 21 -1 4
11 22 -1 -1
5 35 -1 -1
NO
5
9
11 5 3 -1
15 3 4 7
5 2 6 0
6 8 -1 -1
9 6 -1 8
10 1 2 1
2 4 -1 -1
20 7 -1 -1
12 9 -1 -1
NO
6
1
1 1 -1 -1
YES
- 用到了并查集,建立二叉树,二叉树中根遍历,使用队列queue<>判断小堆树
- 保证40分钟内完成,需要经常敲(我花了将近50分钟敲下面的代码直接敲)
/*4 - 09. 笛卡尔树(25)http://www.patest.cn/contests/ds/4-09*/#include <iostream> #include <stdio.h>#include <stdlib.h>#include <vector>#include <string>#include <string.h>#include <algorithm>#include <queue>using namespace std;#define N 1001int n;struct mydata{ int k1; int k2; int left; int right; mydata(int _k1=0, int _k2=0, int _left=-1, int _right=-1) :k1(_k1), k2(_k2), left(_left), right(_right){}};typedef struct node{ int k1, k2; struct node* left; struct node* right; node(int _k1 = 0, int _k2 = 0) :k1(_k1), k2(_k2), left(NULL), right(NULL){}}BNode;int father[N];mydata datas[N];int find(int x){ if (x == father[x]) return x; return father[x] = find(father[x]);}void merg(int x, int y) // 并查集合并{ father[find(y)] = find(x);}BNode* root;BNode* createTreeK1(BNode* root, int i){ if (root == NULL) { root = new node(datas[i].k1,datas[i].k2); if (datas[i].left != -1) { root->left = createTreeK1(root->left, datas[i].left); } if (datas[i].right != -1) { root->right = createTreeK1(root->right, datas[i].right); } } return root;}// 中根遍历vector<int> vin;void inorder(BNode* root){ if (root != NULL) { inorder(root->left); vin.push_back(root->k1); inorder(root->right); }}bool isXiaodui(BNode* root) // 小根堆判断{ queue<BNode*> que; while (!que.empty()) { que.pop(); } que.push(root); while (!que.empty()) { BNode* rt = que.front(); que.pop(); int data = rt->k2; if (rt->left != NULL) { if (rt->left->k2 <= data) return false; que.push(rt->left); } if (rt->right != NULL) { if (rt->right->k2 <= data) return false; que.push(rt->right); } } return true;}int main(){ //freopen("in", "r", stdin); while (scanf("%d", &n) != EOF) { int i; for (i = 0; i < n; i++) { father[i] = i; } for (i = 0; i < n; i++) { scanf("%d%d%d%d", &datas[i].k1, &datas[i].k2, &datas[i].left, &datas[i].right); if (datas[i].left != -1) { if (find(i) != find(datas[i].left)) merg(i, datas[i].left); } if (datas[i].right != -1) { if (find(i) != find(datas[i].right)) merg(i, datas[i].right); } } int rootNum = find(0); root = NULL; root = createTreeK1(root, rootNum); vin.clear(); inorder(root); bool flag1 = true; for (i = 1; i < n; i++) { if (vin[i] <= vin[i - 1]) // 后面的 不大于 前面的就不是了 { flag1 = false; break; } } if (flag1) { bool flag2 = isXiaodui(root); if (flag2) { printf("YES"); } else{ printf("NO"); } } else{ printf("NO"); } printf("\n"); } return 0;}
- 4 - 09. 笛卡尔树(25)
- 4-09. 笛卡尔树(25)(二叉树啊 ZJU_PAT)
- 浙大PAT 4-09. 笛卡尔树 (解题思路)
- 浙大PAT 4-09. 笛卡尔树 (解题思路)
- PAT DS 4-09. 笛卡尔树
- PAT4-09. 笛卡尔树
- poj2201Cartesian Tree(笛卡尔树)
- 笛卡尔树(Cartesian Tree)
- 笛卡尔树
- 笛卡尔树
- 笛卡尔树
- 笛卡尔树
- 笛卡尔树
- 笛卡尔树
- 笛卡尔树
- 笛卡尔树
- 5-31 笛卡尔树 (25分)
- 5-31笛卡尔树(25 分)
- http://www.pan1234.com/result.jsp?wp=0&op=0&ty=gn&q=java面向对象编程
- 在 scala 中 实现 一个方便序列化的 enumeration 类
- 数据库备份与恢复:数据量大的库怎么考虑设计备份策略?
- 【VR】Leap Motion 官网文档 LeapUnityExtensions (LeapUnity扩展)
- 将linux程序或者脚本的后台运行
- 4 - 09. 笛卡尔树(25)
- 简单工厂模式
- Kindle所不为人知的一面
- Xcode/iphone 此证书是由未知颁发机构签名的
- 在Linux上搭建XMPP服务器
- servlet学习笔记8——ServletContext的讲解和使用
- form提交页设置编码类型,使其数据无乱码 gbk utf-8 转
- Git SSH Key 生成步骤
- windows下动态链接库(讲解)