题目链接;http://codeforces.com/problemset/problem/482/B
We'll call an array of n non-negative integers a[1], a[2], ..., a[n]interesting, if it meets m constraints. The i-th of the m constraints consists of three integers li, ri, qi (1 ≤ li ≤ ri ≤ n) meaning that value should be equal to qi.
Your task is to find any interesting array of n elements or state that such array doesn't exist.
Expression x&y means the bitwise AND of numbers x and y. In programming languages C++, Java and Python this operation is represented as "&", in Pascal — as "and".
Input
The first line contains two integers n, m (1 ≤ n ≤ 105, 1 ≤ m ≤ 105) — the number of elements in the array and the number of limits.
Each of the next m lines contains three integers li, ri, qi (1 ≤ li ≤ ri ≤ n, 0 ≤ qi < 230) describing the i-th limit.
Output
If the interesting array exists, in the first line print "YES" (without the quotes) and in the second line print n integersa[1], a[2], ..., a[n] (0 ≤ a[i] < 230) decribing the interesting array. If there are multiple answers, print any of them.
If the interesting array doesn't exist, print "NO" (without the quotes) in the single line.
Sample Input
3 1 1 3 3
YES 3 3 3
3 2 1 3 3 1 3 2
NO
容易发现是线段树的题目,注意题目意思。初始时所有数为0。l,r,q代表区间a[l]&a[l+1]&...a[r]=q。
基本上是线段树模板题。
#include<iostream> #include<cstdio> #include<cstring> #include<algorithm> #include<vector> using namespace std; typedef long long LL; bool judge; int num[100500]; struct node { int start, end; node* left, *right; LL val; node(int start = 0, int end = 0) { this->start = start; this->end = end; this->val=0; this->left = this->right = NULL; } ~node() { if (left != NULL) delete(left); else if (right != NULL) delete(right); left = right = NULL; } }*tree; struct no { int l,r,val; }a[100500]; node* build(int start, int end) { //建树,必须先new出节点 node* nod = new node(start, end); if (start != end) { int mid = (start + end) / 2; nod->left = build(start, mid); nod->right = build(mid + 1, end); } return nod; } void pushdown(node* nod) { if(nod->left) nod->left->val|=nod->val; if(nod->right) nod->right->val|=nod->val; } void pushup(node* nod) { nod->val|=nod->left->val&nod->right->val; } void update(node* nod, int start, int end, LL val) { if(start==nod->start&&end==nod->end) { nod->val|=val; return ; } pushdown(nod); if (end <= nod->left->end) update(nod->left, start, end, val); else if (start >= nod->right->start) update(nod->right, start, end, val); else { update(nod->left, start, nod->left->end, val); update(nod->right, nod->right->start, end, val); } pushup(nod); return; } int query(node* nod,int l,int r) { if(nod->start==l&&nod->end==r) { return nod->val; } if (r <= nod->left->end) return query(nod->left, l, r); else if (l >= nod->right->start) return query(nod->right, l, r); else { return query(nod->left, l, nod->left->end)&query(nod->right, nod->right->start, r); } } void solve(node* nod) { if(!nod) return ; if(nod->start==nod->end) { num[nod->start]=nod->val; return ; } pushdown(nod); solve(nod->left); solve(nod->right); } int main() { int n,m; #ifdef glx freopen("in.txt", "r", stdin); #endif while (cin >> n >> m) { judge = false; //记得必须先new出所有节点 tree=build(1, n); for (int i = 1; i <= m; i++) { scanf("%d%d%d", &a[i].l, &a[i].r, &a[i].val); update(tree, a[i].l, a[i].r, a[i].val); } for(int i=1;i<=m;i++) { if(a[i].val!=query(tree,a[i].l,a[i].r)) { judge=true; break; } } if (judge) cout << "NO" << endl; else { solve(tree); cout << "YES" << endl; cout << num[1]; for (int i = 2; i <= n;i++) cout << " " << num[i]; cout << endl; } delete(tree); } return 0; }