[PKUSC2018]星际穿越

[PKUSC2018]星际穿越

题目大意:

有一排编号为\(1\sim n\)的\(n(n\le3\times10^5)\)个点,第\(i(i\ge 2)\)个点与\([l_i,i-1]\)之间所有点有双向边。\(q(q\le3\times10^5)\)次询问,每次对于\(l_i,r_i,x_i\),求\(\frac{\sum_{y=l_i}^{r_i}dist(x_i,y)}{r_i-l_i+1}\)。

思路:

首先可以得到一个基本结论,从\(x_i\)出发到\(y\)的最短路中,一定存在至少一种满足路径上有且仅有第一步是向右走的。那么我们不妨对于每一个点\(x\),求出\(x\)右侧\(l_i\)最小的\(i=min[x]\),此时\(i\)的覆盖范围一定包含了\(x\)。让\(x\)向\(i\)连边就得到了一个树形结构。在树上每个结点建立主席树维护原图每个点到树上对应结点的距离。

询问时对于\(l_i,r_i,x_i\),若区间\([l_i,r_i]\)内的结点都与\(x_i\)有连边,则答案就是\(r_i-l_i+1\)。否则那些在\(x_i\)连边范围外的那些点到\(x_i\)的距离,就是主席树上到\(min[x_i]\)的距离\(+1\)。到\(min[x_i]\)的距离可以主席树上询问,剩下的\(+1\)一并计算到\(r_i-l_i+1\)中即可。

时间复杂度\(\mathcal O(n\log n)\)。

源代码:

#include<cstdio>
#include<cctype>
#include<algorithm>
inline int getint() {
    register char ch;
    while(!isdigit(ch=getchar()));
    register int x=ch^'0';
    while(isdigit(ch=getchar())) x=(((x<<2)+x)<<1)+(ch^'0');
    return x;
}
const int N=3e5+1,SIZE=N*30;
int left[N],min[N],par[N];
class SegmentTree {
    private:
        struct Node {
            int left,right,tag,sum;
        };
        Node node[SIZE];
        int sz,new_node(const int &p) {
            node[++sz]=node[p];
            return sz;
        }
    public:
        int root[N];
        void modify(int &p,const int &b,const int &e,const int &l,const int &r) {
            p=new_node(p);
            if(b==l&&e==r) {
                node[p].tag++;
                return;
            }
            node[p].sum+=r-l+1;
            const int mid=(b+e)>>1;
            if(l<=mid) modify(node[p].left,b,mid,l,std::min(mid,r));
            if(r>mid) modify(node[p].right,mid+1,e,std::max(mid+1,l),r);
        }
        int query(const int &p,const int &b,const int &e,const int &l,const int &r) {
            if(!p) return 0;
            int ans=node[p].tag*(r-l+1);
            if(b==l&&e==r) return ans+node[p].sum;
            const int mid=(b+e)>>1;
            if(l<=mid) ans+=query(node[p].left,b,mid,l,std::min(mid,r));
            if(r>mid) ans+=query(node[p].right,mid+1,e,std::max(mid+1,l),r);
            return ans;
        }
};
SegmentTree t;
int gcd(const int &a,const int &b) {
    return b?gcd(b,a%b):a;
}
int main() {
    const int n=getint();
    for(register int i=2;i<=n;i++) left[i]=getint();
    min[par[n]=n]=left[n];
    for(register int i=n-1;i;i--) {
        min[i]=std::min(min[i+1],left[i]);
        par[i]=par[min[i]]?:i;
    }
    for(register int i=2;i<=n;i++) {
        if(par[i]==i) t.modify(t.root[i]=t.root[min[i]],1,n,1,i-1);
    }
    for(register int i=2;i<=n;i++) {
        t.root[i]=t.root[i]?:t.root[par[i]];
    }
    for(register int q=getint();q;q--) {
        const int l=getint(),r=getint(),x=getint();
        int ans=r-l+1;
        if(l<left[x]) ans+=t.query(t.root[left[x]],1,n,l,std::min(r,left[x]-1));
        const int d=gcd(ans,r-l+1);
        printf("%d/%d\n",ans/d,(r-l+1)/d);
    }
    return 0;
}

原文地址:https://www.cnblogs.com/skylee03/p/9160594.html

时间: 2024-10-08 14:43:34

[PKUSC2018]星际穿越的相关文章

[PKUSC2018]星际穿越(倍增)

题意:n个点的图,点i和[l[i],i)的所有点连双向边.每次询问(l,r,x)表示x到[l,r]的所有点的最短路径长度和. 首先这题显然可以线段树优化建图,但是需要比较好的常数才能通过45分,还需要发掘性质. 先不考虑往右走的情况,对于一个点x,每个点i与x的最短距离一定形成一个个连续区间,即:设f[i][j]表示i走j步能到的最左的点,则$f[i][j+1]=\min\limits_{k=f[i][j]}^{i-1}l[k]$.所以只要往前扫一遍就能求出f[i]数组. 接着考虑往右走的情况,

「PKUSC2018」星际穿越 (70分做法)

5371: [Pkusc2018]星际穿越 Time Limit: 10 Sec  Memory Limit: 512 MBSubmit: 27  Solved: 11[Submit][Status][Discuss] Description 有n个星球,它们的编号是1到n,它们坐落在同一个星系内,这个星系可以抽象为一条数轴,每个星球都是数轴上的一个点, 特别地,编号为i的星球的坐标是i. 一开始,由于科技上的原因,这n个星球的居民之间无法进行交流,因此他们也不知道彼此的存在. 现在,这些星球独

《星际穿越》关于时间与空间的思考

看完了近期比较火的影片星际穿越,重新刷新了我对世界对宇宙的价值观,可以说这是一部较为实体化把理论把宇宙呈现在观众眼中的影片,让那些不太明白理论的人同样可以感受到宇宙的奥秘,穿梭在宇宙之间,领略着超乎自然神奇力量的世界里,真是一个心旷神怡.相信每一个看完影片的观众都会为之称赞,称赞着自然法则的规律,称赞着科学的伟大,称赞着导演的构思与想象力.影片在现在看来太超前了,也尊重科学,对于科学理论的描述还是最大限度的贴近现有的物理学,除非真的到了那种无法解释而电影又必须用到的地方,导演才展开强大的想象力.

“星际穿越”观后感(宇宙只是界面,科技永远触摸不到世界的本原)

今天刚看完诺兰的“星际穿越”,三个小时的电影确实给人一种震憾的感觉.看完后总有“一种声音”催促自己写上几行. 现在流行各类PAD.智能手机.当阅读长文时,在灵敏的触摸屏上用手指上下拖拉,屏幕上的文字不停快速移动,仿佛屏后有一长卷,在你的指挥下忠实地翻页.其实,这只是一种操作界面,为了照顾我们在日常生活中的习惯,这样安排就无需另附操作手册了.用手指上下拖拉表示滚屏,也可用手指“重按”表示上移,“轻按”表示下移.说到这儿,可能有人会问,这些话不是废话嘛. 莫急,再请用我们的脑子顺便引申一下,不经意间

爱能被量化吗 - 《星际穿越》的两个终极问题

反映宇宙与生命题材的电影,一直都是很难看的,为什么?因为太空里都是慢动作,节奏太慢,不好看:看过天宫一号的“我已出舱,感觉良好”的转播镜头吧?等了十分钟才动了一点点:不要听人吹嘘<2001-太空之旅>如何博大精深,老老实实说人话,正常人坐不住20分钟就得换频道.也不要相信什么最后穿越时空的表现有何震撼,不就是几条彩带么?震什么憾?库布里克的臭脚不要去捧.不好看就是不好看:不要往哲学上靠,要思考哲学问题我直接看书不成么?何必来看你这电影?当年说老库憋了好几年才拍完,很多人硬说是精益求精,依我看那

(纪录片)《星际穿越》中的科学 The Science of Interstellar

简介: 导演: Gail Willumsen编剧: Gail Willumsen主演: 克里斯托弗·诺兰 / 乔纳森·诺兰 / 基普·索恩 / 马修·麦康纳类型: 纪录片 / 短片制片国家/地区: 美国语言: 英语上映日期: 2014-11-25(美国)片长: 41分钟又名: 探索频道:星际穿越的科学IMDb链接: tt4415360 主要内容: 探索频道特别节目<星际穿越>的科学(The Science of Interstellar).<星际穿越>邀请到了物理学家基普·索恩担任

由星际穿越联想到的十维空间

首先声明,本文所述内容纯属个人观点. 库伯镇楼 诺兰天马行空的想象力已然达到了电影尚无以企及的高度,虫洞.高维度空间.黑洞.相对时间,诺兰在电影里面把这些都实现了,让人不可思议,看完这部电影,我不禁思考自身的存在,思考自身所处的空间维度,并花了3个多小时从零维空间推算到十维空间. 零维空间 零维空间是一个点,这个点虽然很简单,但所有维度都是由它组成的. 一维空间 一维空间是由无数个零维空间(点)组成的一条线,我把这条线当做空间的X轴. 二维空间 二维空间是由无数一维空间形成的面,在二维空间,空间

《星际穿越》初解析——一部空前绝后的史诗科学巨作

http://movie.douban.com/review/7188759/ 星际穿越通篇没有一句多余的对白,也没有多余的一个镜头,169分钟超大信息量填满整部电影.这里我打算从两个方面去分析这部电影,一方面是所谓的解析,当然我的天体物理知识有限,只能通过二刷的认知和网上各方面的综合信息得出我的结论,同时也欢迎大家随时指正:另一方面就是从剧作上分析经典桥段和对白,也就是对影片合理性的分析.    一.开篇  从第一镜开始讲.带灰的书架,片名INTERSTELLAR显现.据一位诺兰粉讲,这是诺兰

天体物理学-星际穿越

转载自:?http://www.cnblogs.com/yangpf/p/4148488.html 确实非常喜欢这样的文章,简单的说明白了很多有意思的科学史.天体物理学啊天体物理学.. 以下是原文 本文献给所有爱思考,爱阅读的人 前言 最近去影院看了<星际穿越>,很棒.有种说法是:全体观众都看跪了,一部分是因为影片太棒了,跪了.一部分则是完全没看明白,跪了.影片中出现了牛顿定律,相对论,虫洞,黑洞等概念,而且对这些概念的解释也是点到为止,有些概念甚至没有做任何说明,这样对不爱理科的文科生来说确