zoukankan      html  css  js  c++  java
  • 【THUWC2017】在美妙的数学王国中畅游(bzoj5020)

    我数学是真的菜!!

    清华光用数学知识就把我吊起来打,我还是太菜了


    题解

    如果每座城市的 $f$ 都是 $3$,维护一下树的路径上的 $sum a,space sum b$ 即可。

    其实就是维护一次项和常数项。由于只有两项,所以很好维护。

    这样维护的原理是多项式(这里是一次函数)可以合并,所以要求一条路径的答案,只要把 $x$ 代入这条路径上所有点合并后的多项式即可。

    由于前三个操作需要动态树,套 $LCT$ 即可(我强行再学一遍 $LCT$……)

    但 $sin(ax+b)$ 和 $e(ax+b)$ 都不是多项式,没法合并啊!(也就是说我们只能暴力求路径上每个点的答案再求和)

    然后思考一下,看看题,发现底部给了你一个泰勒展开的公式。

    泰勒展开是什么?就是通过求导数,把一个奇怪的函数展开成多项式。这个多项式的项数无穷多,但我们可以只保留前面若干项,保留的项数越多,这个多项式的结果就越接近原函数的结果。(因为越往后的项,值越接近无穷小,小到 $10^{-???}$ 次方的那种,可以忽略不计)

    再看一下输出要求,答案只要精确到 $10^{-7}$ 就行,然后应该就明白要干什么了……

    泰勒公式:$$f(x)=sum_{i=0}^{n} frac{f^{(i)}(x_0)*(x-x_0)^i}{i!}$$

    其中 $f^{(i)}(x)$ 表示函数 $f(x)$ 的 $i$ 阶导。

    这个公式的 $x_0$  是随便取都可以的,没有区别……只是让你随便代进去一个数而已。

    但是 $x_0=0$ 的时候最方便,上式就变成了 $$f(x)=sum_{i=0}^{n} frac{f^{(i)}(0)*x^i}{i!}$$

    而且这就使函数 $f^{(i)}$ 的自变量 $x=0$ ,也就是说不用管 $x$ 的系数 $a$ 了,在维护时只需要用到它的系数 $b$。下文会再提到。

    然后复习一下怎么求导吧……(雾)

    指数函数求导:$$(a^x)'=a^x*ln a$$

    ($lnspace a$ 代表取自然对数,即底数为 $e$)

    特殊的:$$(e^x)'=e^x$$

    三角函数求导:$$(sin x)'=cos x$$

    $$(cos x)'=-sin x$$

    $$(-sin x)'=-cos x$$

    $$(-cos x)'=sin x$$

    四个一循环,其实就是圆上的四个象限。

    复合函数的求导公式: $$[f(g(x))]'=g'(x) imes f'(g(x))$$

    这道题中,函数 $f$ 就是第一问和第二问要求的那两个式子本身,函数 $g$  则是 $g(x)=ax+b$。

    对于第二问,$f(x)=e^{ax+b}$,则 $f(g(x))=e^{ax+b}$ 求一次导后得到 $$[f(g(x))]'=a imes e^{ax+b}$$

    然后再对 $[f(g(x))]'$ 求导,当时我就有一个没搞明白的地方:为什么 $a$ 求导后不是 $0$?它不是常数项吗?

    后来我才发现,$[f(g(x))]'$ 中的 $a$ 不是常数项,是与变量 $x$ 有关的系数!注意它乘的 $e^{ax+b}$ 里是有个 $x$ 的。

    所以再对 $[f(g(x))]'$ 求导,也就是对 $f(g(x))$ 求二次导时不对若干次项的系数 $a$ 求导,直接乘上即可,重点是对 $e^{ax+b}$ 求导。所以 $$[f(g(x))]''=a^2 imes e^{ax+b}$$

    以此类推,$$[f(g(x))]^{(n)}=a^n imes e^{ax+b}$$

    对于第一问的三角函数求导同理,$$sin'(ax+b)=a cos(ax+b)$$

    $$sin''(ax+b)=-a^2 sin(ax+b)$$

    $$sin'''(ax+b)=-a^3 cos(ax+b)$$

    $$sin''''(ax+b)=a^4 sin(ax+b)$$

    以此类推的循环。

    由于我们之前让自变量 $x=x_0=0$ 了,所以实际维护以上所有信息时不用算和 $x$ 相关的项(而且输入的 $x$ 不唯一,本身就没法维护。这就是为什么让那个随意值 $x_0$ 为 $0$ 会很方便)。

      1 #include<bits/stdc++.h>
      2 #define ll long long
      3 #define rep(i,x,y) for(int i=x;i<=y;++i)
      4 #define N 200002
      5 #define M 16
      6 using namespace std;
      7 inline int read(){
      8     int x=0; bool f=1; char c=getchar();
      9     for(;!isdigit(c);c=getchar()) if(c=='-') f=0;
     10     for(; isdigit(c);c=getchar()) x=(x<<3)+(x<<1)+(c^'0');
     11     if(f) return x;
     12     return 0-x;
     13 }
     14 int n,m,k,f[N];
     15 char type[2];
     16 double jc[N],sum[N][M],a[N],b[N];
     17 int ch[N][2],fa[N];
     18 bool rev[N];
     19 
     20 ;inline bool son(int x){return ch[fa[x]][1]==x;}
     21 inline bool isroot(int x){return ch[fa[x]][0]!=x && ch[fa[x]][1]!=x;}
     22 inline void reverse(int x){
     23     if(!x) return;
     24     swap(ch[x][0],ch[x][1]), rev[x]^=1;
     25 }
     26 void pushup(int x){
     27     rep(i,0,M-1) sum[x][i]=sum[ch[x][0]][i]+sum[ch[x][1]][i];
     28     if(f[x]==1){
     29         double val=1,Sin=sin(b[x]),Cos=cos(b[x]);
     30         for(int i=0;i<M;i+=4){
     31             sum[x][i]+=Sin*val, val*=a[x];
     32             sum[x][i+1]+=Cos*val, val*=a[x];
     33             sum[x][i+2]-=Sin*val, val*=a[x];
     34             sum[x][i+3]-=Cos*val, val*=a[x];
     35         }
     36     }
     37     else if(f[x]==2){
     38         double val=exp(b[x]); sum[x][0]+=val;
     39         for(int i=1;i<M;++i)
     40             val*=a[x], sum[x][i]+=val;
     41     }
     42     else
     43         sum[x][0]+=b[x], sum[x][1]+=a[x];
     44 }
     45 void pushdown(int x){
     46     if(!rev[x]) return;
     47     reverse(ch[x][0]), reverse(ch[x][1]), rev[x]=0;
     48 }
     49 void rotate(int x){
     50     int f=fa[x], g=fa[f], c=son(x);
     51     ch[f][c]=ch[x][c^1];
     52     if(ch[f][c]) fa[ch[f][c]]=f;
     53     fa[x]=g;
     54     if(!isroot(f)) ch[g][son(f)]=x;
     55     ch[x][c^1]=f, fa[f]=x, pushup(f);
     56 }
     57 int stk[N],top;
     58 void splay(int x){
     59     stk[++top]=x;
     60     for(int i=x;!isroot(i);i=fa[i]) stk[++top]=fa[i];
     61     while(top) pushdown(stk[top--]);
     62     for(;!isroot(x);rotate(x))
     63         if(!isroot(fa[x])) son(x)^son(fa[x]) ? rotate(x) : rotate(fa[x]);
     64     pushup(x);
     65 }
     66 void access(int x){
     67     for(int y=0; x; y=x,x=fa[x])
     68         splay(x), ch[x][1]=y, pushup(x);
     69 
     70 }
     71 void makeroot(int x){
     72     access(x), splay(x), reverse(x);
     73 }
     74 int findroot(int x){
     75     access(x), splay(x);
     76     while(ch[x][0]) x=ch[x][0];
     77     splay(x); return x;
     78 }
     79 void split(int x,int y){
     80     makeroot(x), access(y), splay(y);
     81 }
     82 void link(int x,int y){
     83     makeroot(x), fa[x]=y;
     84 }
     85 void cut(int x,int y){
     86     split(x,y), ch[y][0]=fa[x]=0;
     87 }
     88 
     89 inline void getJc(){
     90     jc[0]=jc[1]=1;
     91     rep(i,2,M-1) jc[i]=jc[i-1]*i;
     92 }
     93 int main(){
     94     getJc();
     95     n=read(),m=read();
     96     scanf("%s",type);
     97     rep(i,1,n) scanf("%d %lf %lf",&f[i],&a[i],&b[i]);
     98     while(m--){
     99         int u,v,ff;
    100         double aa,bb,x,IQ,ans;
    101         char s[10];
    102         scanf("%s",s);
    103         if(s[0]=='a'){
    104             u=read()+1,v=read()+1;
    105             link(u,v);
    106         }
    107         else if(s[0]=='d'){
    108             u=read()+1,v=read()+1;
    109             cut(u,v);
    110         }
    111         else if(s[0]=='m'){
    112             scanf("%d %d %lf %lf",&u,&ff,&aa,&bb);
    113             ++u;
    114             makeroot(u);
    115             f[u]=ff, a[u]=aa, b[u]=bb;
    116             pushup(u);
    117         }
    118         else{
    119             scanf("%d %d %lf",&u,&v,&IQ);
    120             x=1, ++u, ++v;
    121             if(findroot(u)^findroot(v)){
    122                 printf("unreachable
    ");
    123                 continue;
    124             }
    125             split(u,v);
    126             ans=0;
    127             rep(i,0,M-1)
    128                 ans+=sum[v][i]*x/jc[i], x*=IQ;
    129             printf("%.8e
    ",ans);
    130         }
    131     }
    132     return 0;
    133 }
    View Code

    如果你数学学得好,这题就是个 $LCT$ 裸题(前提是你能熟练秒切 $LCT$)

    然而裸题效果对我明显无效

  • 相关阅读:
    Working with WordprocessingML documents (Open XML SDK)
    How to Choose the Best Way to Pass Multiple Models in ASP.NET MVC
    Azure:Manage anonymous read access to containers and blobs
    Convert HTML to PDF with New Plugin
    location.replace() keeps the history under control
    On the nightmare that is JSON Dates. Plus, JSON.NET and ASP.NET Web API
    HTTP Modules versus ASP.NET MVC Action Filters
    解读ASP.NET 5 & MVC6系列(6):Middleware详解
    Content Negotiation in ASP.NET Web API
    Action Results in Web API 2
  • 原文地址:https://www.cnblogs.com/scx2015noip-as-php/p/bzoj5020.html
Copyright © 2011-2022 走看看