题目背景
滚粗了的HansBug在收拾旧英语书,然而他发现了什么奇妙的东西。
题目描述
udp2.T3如果遇到相同的字符串,输出后面的
蒟蒻HansBug在一本英语书里面找到了一个单词表,包含N个单词(每个单词内包含大小写字母)。现在他想要找出某一段连续的单词内字典序最大的单词。
输入输出格式
输入格式:
第一行包含两个正整数N、M,分别表示单词个数和询问个数。
接下来N行每行包含一个字符串,仅包含大小写字母,长度不超过15,表示一个单词。
再接下来M行每行包含两个整数x、y,表示求从第x到第y个单词中字典序最大的单词。
输出格式:
输出包含M行,每行为一个字符串,分别依次对应前面M个询问的结果。
输入输出样例
说明
样例说明:
第一次操作:在{absi,hansbug,lzn,kkk,yyy}中找出字典序最大的,故为yyy
第二次操作:在{absi}中找出字典序最大的,故为absi
第三次操作:在{absi,hansbug}中找出字典序最大的,故为hansbug
第四次操作:在{hansbug,lzn}中找出字典序最大的,故为lzn
第五次操作:在{kkk}中找出字典序最大的,故为kkk
数据规模:
注意事项:1.该题目单词字典序比对过程中大小写不敏感,但是输出必须输出原单词
2.该题目时间限制为0.2s
// luogu-judger-enable-o2
//6哇
//单词长度不超过15,我可不可以直接在树里存string?233
//决定也把我的线段树写成指针
//决定以后不写 using namespace std;
//我要杀了这道题tmd
//。手写比较函数不知道为啥就错了,mmp啊
//浪费时间
//指针线段树真是吃翔了
//made
#include<iostream>
#include<cstdio>
#include<cmath>
#include<cstring>
#include<string>
#include<algorithm>
#include<cctype>
using std::string;
using std::cin;
using std::cout;
const int N=5e4+5;
int n,m;
struct NODE
{
int l,r,mid;
NODE *son[2];
string s,maxs;
}node[N<<2];
struct ANS
{
string s,maxs;
}ans;
typedef NODE* Tree;
Tree Root,now_node=node;
inline int read()
{
char c=getchar();int num=0;
for(;!isdigit(c);c=getchar());
for(;isdigit(c);c=getchar())
num=num*10+c-'0';
return num;
}
inline void update(Tree root)
{
if(root->son[0]->maxs>root->son[1]->maxs)
{
root->s=root->son[0]->s;
root->maxs=root->son[0]->maxs;
}
else
{
root->s=root->son[1]->s;
root->maxs=root->son[1]->maxs;
}
// cout<<root->l<<" "<<root->r<<'\n'<<"s: "<<root->s<<" maxs: "<<root->maxs<<'\n';
}
void build(Tree &root,int l,int r)
{
root=++now_node;
root->l=l,root->r=r,root->mid=l+r>>1;
if(l==r)
{
cin>>root->s;
root->maxs=root->s;
transform(root->maxs.begin(),root->maxs.end(),root->maxs.begin(),toupper);
// cout<<root->s;
return;
}
build(root->son[0],l,root->mid);
build(root->son[1],root->mid+1,r);
update(root);
}
void query(Tree root,int l,int r)
{
if(l==root->l&&r==root->r)
{
if((root->maxs)>=(ans.maxs)||ans.s=="")
{
ans.s=root->s;
ans.maxs=root->maxs;
}
return;
}
if(r<=root->mid)
query(root->son[0],l,r);
else if(l>root->mid)
query(root->son[1],l,r);
else
{
query(root->son[0],l,root->mid);
query(root->son[1],root->mid+1,r);
}
}
int main()
{
n=read(),m=read();
build(Root,1,n);
for(int i=1,l,r;i<=m;++i)
{
l=read(),r=read();
ans.s="",ans.maxs="";
query(Root,l,r);
cout<<ans.s<<'\n';
}
return 0;
}
来源:https://www.cnblogs.com/lovewhy/p/8747040.html