列表

详情


NC206979. 木桩

描述

现有 n 根木桩,长度为 n 的正整数数组 a 中的 ai 表示第 i 根木桩的高度。小明现在获得了一个木桩高度更改器,他能够控制更改器在高度 H 从左到右发射出一条更改光线;光线能够将照射到的第一根木桩 (第一根高度不低于H 的木桩) 高度更改为 h 。当小明发射完 m 条射线后,他想知道现在所有木桩的高度,你能帮帮他吗?

输入描述

第一行包含一个整数 T ( 1 ≤ T ≤ 10 ) 表示共有T组测试样例
接下来每组的第一行有两个整数n , m ( 1 ≤ n , m ≤ 1e5 )
n - 木桩数量
m - 光线数量
接下来一行包含 n 个整数 a1 , a2 ··· an ( 0 ≤ ai ≤ 1e6 ) 表示木桩高度
接下来 m 行,每行包含两个整数 H , h ( 0 ≤ H , h ≤ 1e6 )
H - 发射射线高度
h - 照射后更改的木桩高度

输出描述

每组输出 n 个整数,对应最终的木桩高度,每两个数之间用空格隔开。

示例1

输入:

2
5 2
5 4 3 2 1
2 1
2 3
5 3
5 4 3 2 1
2 6
1 4
5 5

输出:

1 3 3 2 1
4 4 3 2 1

原站题解

上次编辑到这里,代码来自缓存 点击恢复默认模板

C++11(clang++ 3.9) 解法, 执行用时: 868ms, 内存消耗: 28636K, 提交时间: 2020-06-08 12:18:18

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

int a[100005], segtree[400020];

void build(int l,int r,int root){
	if(l == r) segtree[root]=a[l];
	else{
		int mid = (l+r)>>1;
		build(l,mid,root<<1);
		build(mid+1,r,root<<1|1);
		segtree[root] = max(segtree[root<<1],segtree[root<<1|1]);
	}
}

int update(int l,int r,int root,int H,int h){
	if(segtree[root]<H) return 0;
	if(l==r){
		segtree[root]=h;
		return l;
	}
	int mid = (l+r)>>1, p;
	if(segtree[root<<1]>=H) p = update(l,mid,root<<1,H,h);
	else p = update(mid+1,r,root<<1|1,H,h);
	segtree[root] = max(segtree[root<<1],segtree[root<<1|1]);
	return p;
}

int main(){
	int T;
	scanf("%d",&T);
	while(T--){
		int n, m;
		scanf("%d %d",&n,&m);
		for(int i = 1;i <= n;i++)
			scanf("%d",&a[i]);
		build(1,n,1);
		while(m--){
			int H, h;
			scanf("%d%d",&H,&h);
			int p = update(1,n,1,H,h);
			a[p]=h;
		}
		for(int i = 1;i < n;i++)
			printf("%d ",a[i]);
		printf("%d\n",a[n]);
	}
	return 0;
} 

C++14(g++5.4) 解法, 执行用时: 700ms, 内存消耗: 10608K, 提交时间: 2020-06-07 14:56:45

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

struct book
{
	int l, r, v;
}a[4000005];

int vl[1000005];

void make(int left, int right, int num)
{
	a[num].l=left;
	a[num].r=right;
	if(a[num].l==a[num].r)
		a[num].v=vl[left];
	else
	{
		make(left,(left+right)/2,num*2);
		make((left+right)/2+1,right,num*2+1);
		a[num].v=max(a[num*2].v, a[num*2+1].v);
	}
}

void Q(int H, int h, int num)
{
	if(a[num].l == a[num].r)
	{
		a[num].v = h;
		vl[a[num].l] = h;
		return ;
	}
	if(H > a[num].v)
		return ;
	else
	{
		if(H <= a[num*2].v)
			Q(H,h,num*2);
		else
			Q(H,h,num*2+1);
	}
	a[num].v=max(a[num*2].v, a[num*2+1].v);
}

int main()
{
	int t = 1;
	scanf("%d", &t);
	while(t--)
	{
		int n, q;
		scanf("%d %d", &n, &q);
		for(int i = 1; i <= n; i++)
			scanf("%d", &vl[i]);
		make(1,n,1);
		while(q--)
		{
			int H, h;
			scanf("%d %d", &H, &h);
			Q(H,h,1);
		}
		for(int i = 1; i <= n; i++)
			printf("%d ", vl[i]);
		printf("\n");
	}
}

上一题