tg 74 solution

tg 74 solution

T1

暴搜题

这个sb在赛时打了个垃圾暴搜

事实上你打个表就可能会发现结论

下面给出一个构造方案并给出严谨证明

就是首先两个数组分别填上12

然后每次考虑从i1i

新增的部分考虑将对方复制然后加上2i接在自己的后面

给出证明:

设当前答案数组a,b

显然n=1的时候,我们的初始答案是合法的

p[0,n),i=1paip=i=1pbip

假设n=t,tN+的时候,记size=2t

p[0,t),i=1paip=i=1pbip

此时:nt+1,

i[size+1,2size),aibisize+2t,bibisize+2t

i=size+12sizeaip=i=1size(bi+2t)p

i=size+12sizeaip=i=1sizej=1pCpjbij

此时我们提出组合数

i=size+12sizeaip=j=1pCpji=1sizebij

同理,把i=size+12sizebip换掉,有

i=size+12sizebip=j=1pCpji=1sizeaij

不巧的是,p[0,t),i=1paip=i=1pbip

于是p=[0,t)的部分就结束了

然后就是如果p=t的话两边式子做个差,

你会发现两个最高次项消没了,于是剩下的又是系数相等,

于是就证完了


T2

"zazheng"

"zuotianhackwo" "jintiannihailai"

首先记Si={VE},V=[1,i],(u,v)E,uV,vV

显然的,i,SiG对吧

事实上,我们只需要知道SiSi1

就可以知道i[1,i1)中的点连了多少条边

事实上,记f(x)表示[1,x]中所有点向x连的边数

显然的,f(x)随着x的增大单调不降,

因为差分的意义就是xi有没有连边,也不可能出负数......

单调了二分出所有改变点就不难了

对于一次二分的过程是:

一开始l是上一个拐点,r就是固定右端点

mid=l+r2

f(mid)=f(l)时,lmid+1

否则rmid

一直二分到l=r此时l就是一个和x连边的点

显然,fmid可以通过询问Vmid\orx减去|Emid|得到,而|Emid|可以预处理每次一个询问得到

对于每个点i持续进行上述二分即可确定所有边

每条边一次二分,算上预处理,询问次数n+mlogn

T3

线段树,

势能分析表明时间复杂度是对的

直接放码了

点击查看代码


#include <bits/stdc++.h>
using namespace std;
#define D double 
const int o=2222222,u=43;
const D cosin=0.73908513321516064166;
ifstream fin("excalibur.in");
ofstream fout("excalibur.out");
int n,m,L,R;
D a[o],P[u];
struct SgT{
    D val[o][u];
    int num[o],lazy[o],cov[o];
    void up(int p){
        num[p]=0;
        int ls=p*2,rs=p*2+1;
        for(int i=0,l=num[ls],r=num[rs];i<u;i++){
            val[p][i]=val[ls][l]+val[rs][r];
            l++,r++;
            l=(l==u?0:l);
            r=(r==u?0:r);
        }
    }
    void build(int p,int l,int r){
        if(l==r){
            val[p][0]=a[l];
            for(int i=1;i<u;i++)
                val[p][i]=cos(val[p][i-1]);
            return;
        }
        int mid=(l+r)/2;
        build(p*2,l,mid);
        build(p*2+1,mid+1,r);
        up(p);
    }
    void down(int p,int l,int r){
        int ls=p*2,rs=p*2+1;
        int mid=(l+r)/2;
        if(cov[p]){
            cov[ls]=cov[rs]=cov[p];
            num[ls]=num[rs]=num[p];
            lazy[ls]=lazy[rs]=0;
            D k=(mid-l+1.0)/(r-l+1.0);
            for(int i=0;i<u;i++)
                val[ls][i]=val[p][i]*k;
            k=1-k;
            for(int i=0;i<u;i++)
                val[rs][i]=val[p][i]*k;
            cov[p]=lazy[p]=0;
        }
        if(lazy[p]>0){
            int t=max(0,min(lazy[p],u-lazy[ls]));
            D v=cosin*(mid-l+1);lazy[ls]+=t;
            for(int i=1,&x=num[ls];i<=lazy[p];i++){
                val[ls][x]=v;x++;
                x=(x==u?0:x);
            }
            t=max(0,min(lazy[p],u-lazy[rs]));
            v=cosin*(r-mid);lazy[rs]+=t;
            for(int i=1,&x=num[rs];i<=lazy[p];i++){
                val[rs][x]=v;x++;
                x=(x==u?0:x);
            }
            lazy[p]=0;
        }
    }
    void cover(int p,int l,int r){
        if(L<=l&&r<=R){
            cov[p]=1;
            lazy[p]=num[p]=0;
            for(int i=0;i<u;i++)
                val[p][i]=P[i]*(r-l+1);
            return;
        }
        down(p,l,r);int mid=(l+r)/2;
        if(L<=mid)cover(p*2,l,mid);
        if(R>mid)cover(p*2+1,mid+1,r);
        up(p);
    }
    void change(int p,int l,int r){
        if(val[p][num[p]]==cosin*(r-l+1))return;
        if(L<=l&&r<=R){
            lazy[p]++;
            val[p][num[p]]=cosin*(r-l+1);
            num[p]++;
            num[p]=(num[p]==u?0:num[p]);
            return ;
        }
        down(p,l,r);int mid=(l+r)/2;
        if(L<=mid)change(p*2,l,mid);
        if(R>mid)change(p*2+1,mid+1,r);
        up(p);
    }
    D ques(int p,int l,int r){
        if(val[p][num[p]]==cosin*(r-l+1))
            return cosin*(min(r,R)-max(l,L)+1);
        if(L<=l&&r<=R)
            return val[p][num[p]];
        down(p,l,r);
        int mid=(l+r)/2;D ans=0;
        if(L<=mid)ans+=ques(p*2,l,mid);
        if(R>mid)ans+=ques(p*2+1,mid+1,r);
        return ans;
    }
}T;
void in(){
    fin>>n>>m;
    for(int i=1;i<=n;i++)fin>>a[i];
}
void work(){
    T.build(1,1,n);
    for(int i=1;i<=m;i++){
        int op;
        fin>>op>>L>>R;
        if(op==1)T.change(1,1,n);
        if(op==2)fout<<fixed<<setprecision(8)<<T.ques(1,1,n)<<"\n";
        if(op==3){
            fin>>P[0];
            for(int j=1;j<u;j++)P[j]=cos(P[j-1]);
            T.cover(1,1,n);
        }
    }
}
int main(){
    ios::sync_with_stdio(0);
    fin.tie(0),fout.tie(0);
    in();work();
    return 0;
}

T4

posted @   2K22  阅读(18)  评论(0编辑  收藏  举报
编辑推荐:
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 基于Microsoft.Extensions.AI核心库实现RAG应用
· Linux系列:如何用heaptrack跟踪.NET程序的非托管内存泄露
· 开发者必知的日志记录最佳实践
阅读排行:
· winform 绘制太阳,地球,月球 运作规律
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· AI 智能体引爆开源社区「GitHub 热点速览」
· Manus的开源复刻OpenManus初探
· 写一个简单的SQL生成工具
点击右上角即可分享
微信分享提示