【HDU】4092 Nice boat(多校第四场1006) ——线段树 懒惰标记
Nice boat
Time Limit: 30000/15000 MS (Java/Others) Memory Limit: 131072/131072 K (Java/Others)
Total Submission(s): 146 Accepted Submission(s): 75
Also, this devil is looking like a very cute Loli.
Let us continue our story, z*p(actually you) defeat the 'MengMengDa' party's leader, and the 'MengMengDa' party dissolved. z*p becomes the most famous guy among the princess's knight party.
One day, the people in the party find that z*p has died. As what he has done in the past, people just say 'Oh, what a nice boat' and don't care about why he died.
Since then, many people died but no one knows why and everyone is fine about that. Meanwhile, the devil sends her knight to challenge you with Algorithm contest.
There is a hard data structure problem in the contest:
There are n numbers a_1,a_2,...,a_n on a line, everytime you can change every number in a segment [l,r] into a number x(type 1), or change every number a_i in a segment [l,r] which is bigger than x to gcd(a_i,x) (type 2).
You should output the final sequence.
For each test case, the first line contains a integers n.
The next line contains n integers a_1,a_2,...,a_n separated by a single space.
The next line contains an integer Q, denoting the number of the operations.
The next Q line contains 4 integers t,l,r,x. t denotes the operation type.
T<=2,n,Q<=100000
a_i,x >=0
a_i,x is in the range of int32(C++)
Please output a single more space after end of the sequence
题意:给定一个数字序列,对其进行两种操作:1、将序列中连续的一段变成一样的数x;2、给序列中连续的一段和一个数x,对于这个连续一段中的每个数,如果小于x则取x与这个数的最大公约数,否则不操作。
题解:线段树+懒人标记
代码:
#include <cstdio>
#include <cstring> const int LEN = ; struct line
{
int left;
int right;
int value;
}line[LEN*];
int point[LEN*]; //记录线段树底层节点的位置 inline int gcd(int a,int b) //求最大公约数
{
return a % b ? gcd(b, a % b) : b;
} void buildt(int left, int right, int step) //建树同时初始化懒惰标记
{
line[step].value = -;
line[step].left = left;
line[step].right = right;
if (left == right){
point[left] = step;
return;
}
int mid = (left + right) / ;
buildt(left, mid, step*);
buildt(mid+, right, step*+);
} void query_1(int left, int right, int x, int step) //操作一
{
if (left == line[step].left && right == line[step].right){
line[step].value = x;
return;
}
if (line[step].value != -){
line[step*].value = line[step*+].value = line[step].value;
line[step].value = -;
}
int mid = (line[step].left + line[step].right) / ;
if (right <= mid)
query_1(left, right, x, step*);
else if (left > mid)
query_1(left, right, x, step*+);
else{
query_1(left, mid, x, step*);
query_1(mid+, right, x, step*+);
}
} void query_2(int left, int right, int x, int step) //操作函数二
{
if (line[step].left == left && line[step].right == right){
if (line[step].value != -){ //如果找到对应区间,且有标记,则进行条件判断,否则继续
if (line[step].value > x)
line[step].value = gcd(line[step].value, x);
return;
}
}
if (line[step].value != -){ //如果改点被标记,则下移一层
line[step*].value = line[step*+].value = line[step].value;
line[step].value = -;
}
int mid = (line[step].left + line[step].right) / ;
if (right <= mid)
query_2(left, right, x, step*);
else if (left > mid)
query_2(left, right, x, step*+);
else{
query_2(left, mid, x, step*);
query_2(mid+, right, x, step*+);
}
} void findans(int left, int right, int step) //dfs输出结果
{
if (line[step].left == left && line[step].right == right){
if (line[step].value != -){
for(int i = ; i < line[step].right - line[step].left + ; i++)
printf("%d ", line[step].value);
return;
}
}
if (line[step].value != -){
line[step*].value = line[step*+].value = line[step].value;
line[step].value = -;
}
int mid = (line[step].left + line[step].right) / ;
if (right <= mid)
findans(left, right, step*);
else if (left > mid)
findans(left, right, step*+);
else{
findans(left, mid, step*);
findans(mid+, right, step*+);
}
} int main()
{
int T;
//freopen("in.txt", "r", stdin);
scanf("%d", &T);
while(T--){
int n;
memset(point, , sizeof(point));
scanf("%d", &n);
buildt(, n, );
for(int i = ; i <= n; i++){
int t;
scanf("%d", &t);
line[point[i]].value = t;
}
int m;
scanf("%d", &m);
for(int i = ; i < m; i++){
int t, l, r, x;
scanf("%d %d %d %d", &t, &l, &r, &x);
if (t == ){
query_1(l, r, x, );
}
else if (t == ){
query_2(l, r, x, );
}
}
findans(, n, );
printf("\n");
}
return ;
}
【HDU】4092 Nice boat(多校第四场1006) ——线段树 懒惰标记的更多相关文章
- 2014多校第四场1006 || HDU 4902 Nice boat (线段树 区间更新)
题目链接 题意 : 给你n个初值,然后进行两种操作,第一种操作是将(L,R)这一区间上所有的数变成x,第二种操作是将(L,R)这一区间上所有大于x的数a[i]变成gcd(x,a[i]).输出最后n个数 ...
- 2019牛客多校第四场A meeting——树的直径
题意: 一颗 $n$ 个节点的树上标有 $k$ 个点,找一点使得到 $k$ 个关键结点的最大距离最小. 分析: 问题等价于求树的直径,最小距离即为直径除2向上取整. 有两种求法,一是动态规划,对于每个 ...
- hdu6606多校第四次04——线段树加速dp
/* 首先想到二分答案,难点在于如何判断是否有K段,每段和<=mid 把问题转化成求最多有R段,最少有L段,每段的的和<=mid,如果 L<=K<=R 那么显然存在把这个序列分 ...
- 牛客多校第四场 A meeting 树的半径
题意: 有一棵树,树上有许多人,他们要聚会,找一个点使得所有人到这个点的距离的最大值最小. 题解: 首先,以一个有人的点为根,求一个生成树,删掉所有没有人的子树,保证所有的悬挂点(只连接一条边的点)都 ...
- Transformation HDU - 4578(线段树——懒惰标记的妙用)
Yuanfang is puzzled with the question below: There are n integers, a 1, a 2, …, a n. The initial val ...
- 2018 HDU多校第四场赛后补题
2018 HDU多校第四场赛后补题 自己学校出的毒瘤场..吃枣药丸 hdu中的题号是6332 - 6343. K. Expression in Memories 题意: 判断一个简化版的算术表达式是否 ...
- 牛客多校第四场sequence C (线段树+单调栈)
牛客多校第四场sequence C (线段树+单调栈) 传送门:https://ac.nowcoder.com/acm/contest/884/C 题意: 求一个$\max {1 \leq l \le ...
- 2016暑假多校联合---Rikka with Sequence (线段树)
2016暑假多校联合---Rikka with Sequence (线段树) Problem Description As we know, Rikka is poor at math. Yuta i ...
- 牛客多校第3场 J 思维+树状数组+二分
牛客多校第3场 J 思维+树状数组+二分 传送门:https://ac.nowcoder.com/acm/contest/883/J 题意: 给你q个询问,和一个队列容量f 询问有两种操作: 0.访问 ...
随机推荐
- bzoj1644 [Usaco2007 Oct]Obstacle Course 障碍训练课
Description 考虑一个 N x N (1 <= N <= 100)的有1个个方格组成的正方形牧场.有些方格是奶牛们不能踏上的,它们被标记为了'x'.例如下图: . . B x . ...
- sql必知必会(第四版) 学习笔记二 视图
本书用到的几个表的建表sql语句如下: --销售产品供应商 CREATE TABLE Vendors ( vend_id varchar(20) not null, vend_name varchar ...
- 极致精简的fragment实现导航栏切换demo
一个小demo.用button+fragment实现导航栏切换界面,适合刚接触的新手看一下. 效果图 点击第二个后 源码: 主界面 <span style="font-size:18p ...
- Mongoose的模糊查询
var Commidity = require("./Model/commiditiesModel"); function search(response,request,key) ...
- C#中WinForm程序退出方法技巧总结
C#中WinForm程序退出方法技巧总结 一.关闭窗体 在c#中退出WinForm程序包括有很多方法,如:this.Close(); Application.Exit();Application.Ex ...
- SQL中Truncate的用法(转)
转自:http://www.studyofnet.com/news/555.html 本文导读:删除表中的数据的方法有delete,truncate, 其中TRUNCATE TABLE用于删除表中的所 ...
- hdu3123GCC
Problem Description The GNU Compiler Collection (usually shortened to GCC) is a compiler system prod ...
- HDU 1088 - Write a simple HTML Browser
直接看sample input = = 又一道模拟. #include <iostream> #include <string> #include <cstdio> ...
- Ubuntu安装中文字体
Ubuntu没有宋体,楷体之类的中文字体,在Libreoffice中打不出中文,-_-! 我们可以从windows中借点字体过来,哈哈. 一.准备字体 从windows7中拷贝出字体文件,拷贝的目录为 ...
- c++ iostream 相关使用
索引: C++的iostream标准库介绍+使用详解(转) iostream格式化输出 c++ 字符串流 sstream(常用于格式转换) 关于#include <iomanip>中iom ...