首页 > 其他分享 >【题目】ccf csp 202309-3 梯队求解

【题目】ccf csp 202309-3 梯队求解

时间:2024-03-12 11:02:00浏览次数:22  
标签:ccf 202309 int include str ori div x1 csp

题目大意:给出需要求解的逆波兰表达式(后缀表达式),包含多个变量,现在每一次查询,给出所有变量的值,询问对于给定的变量其函数偏导值为多少。(仅包含乘、加减运算)

(例如,对于表达式:

x1 x1 x1 * x2 + *

可转化为(x1 * x1 + x2) * x1

对x1求偏导后变为(2 * x1 + x2) + (x1 * x1 + x2)

带入x1 = 2,x2 = 3可以得到 (2 * 2 + 3) + (2 * 2 + 3) = 7 + 7 = 14)

考虑递归迭代地解决问题,我们把表达式视为一棵树,我们得到了一个根结点为运算,叶子结点为常数或变量的二叉树。

例如,上式可化作:

我们敏锐地发现,如果按照平常的习惯,从上往下遍历这棵树来求导,仅有乘法会需要下一层的两种运算法则的结果:原始计算结果和求导计算结果。

考虑到,直接存储求导后的表达式显然是不现实的,我们的目标是通过仅存储数值来完成两种运算。因此,我们对每个节点设置两个值:原始计算结果和求导计算结果。这样,每当遇到乘法节点t,设其儿子分别为s1,s2,求导结果为div,原始结果为ori,可以得到

t.div = s1.div * s2.ori + s1.ori * s2.div

t.ori = s1.ori * s2.ori

这里仅仅表述了最复杂的乘法节点如何计算。对于叶子节点l,若为自变量则l.div = 1, l.ori = value。

因此,根据后缀表达式从下向上处理每个节点,最终能得到每个节点所代表的子树的求导和原始结果。

AC代码:

#include <cstdio>
#include <iostream>
#include <algorithm>
#include <cstring>
#include <string>
#include <cstdlib>

#define up(l,r,i) for(int i=l;i<=r;i++)
#define dn(l,r,i) for(int i=r;i>=l;i--)

#define ll long long

using namespace std;

const int MAXN = 130, MAXM = 102;
const int MOD = 1e9+7;

int n,m;

string str;

ll stacK[MAXN][2];//0 ori 1 div
int scnt;

int nums[MAXN];

int x;

void push(int a,int b){
    stacK[++scnt][0] = a;
    stacK[scnt][1] = b;
}



void solve(){

    up(0,str.size(),i){
        if(str[i] == ' '){continue;}
        else if(str[i] == 'x'){
            int cnt = 0;
            while(str[i+1+cnt] != ' ')
                cnt++;
            int  num = atoi(str.substr(i+1,cnt).c_str());
            i += cnt+1;
            push(nums[num],(x==num)?1:0);
            //cout<<"x"<<num<<endl;
        }
        else if(str[i] == '*'){
            ll a = stacK[scnt][0];
            ll b = stacK[scnt--][1];
            ll c = stacK[scnt][0];
            ll d = stacK[scnt--][1];
            push((a*c)%MOD,((a*d)%MOD + (b*c)%MOD)%MOD);
        }
        else if(str[i] == '+'){
            ll a = stacK[scnt][0];
            ll b = stacK[scnt--][1];
            ll c = stacK[scnt][0];
            ll d = stacK[scnt--][1];
            push((a + c)%MOD,(b + d)%MOD);
        }
        else if(str[i] == '-'){
            if(str[i+1] == ' '){
                ll a = stacK[scnt][0];
                ll b = stacK[scnt--][1];
                ll c = stacK[scnt][0];
                ll d = stacK[scnt--][1];
                push((c - a)%MOD,(d - b)%MOD);
            }
            else{
                int cnt = 0;
                while(str[i+1+cnt] != ' ') cnt++;
                ll num = atoi(str.substr(i,cnt+1).c_str());
                i += cnt+1;
                //cout<<"-n"<<num<<endl;
                push(num,0);
            }
        }
        else if('0' <= str[i] && str[i] <= '9'){
            int cnt = 0;
            while(str[i+cnt] != ' ') cnt++;
            ll num = atoi(str.substr(i,cnt).c_str());
            i += cnt;
            push(num,0);
            //cout<<"n"<<num<<endl;
        }

    }
}


int main()
{
    cin>>n>>m; 
    getchar();
    str.resize(1000);
    getline(cin, str);
    str += ' ';

    up(1,m,ii){
        cin>>x;
        up(1,n,i)
            cin>>nums[i];
        scnt = 0;
        solve();
        if(stacK[1][1] < 0) stacK[1][1] += MOD;
        cout<<stacK[1][1]<<endl;
    }

    return 0;
}
View Code

 

标签:ccf,202309,int,include,str,ori,div,x1,csp
From: https://www.cnblogs.com/dudujerry/p/18067834

相关文章

  • CSP2023 游记
    CSP2023游记Day0(10.20)上午whk没啥说的下午请假润去九江,住了一个离考场几百米的酒店,一层几乎全是OIerstOdalaoOrz晚上去酒店旁边的万达吃了个饭,然后去考场转了一圈凌晨,睡不着,根本睡不着Day1(10.21)上午6:30起床6:50吃饭7:30出发去考场8:00进考场面基试机......
  • 2023 CSP-S游记
    DAY-3~-2请假啦真爽,直接起洞上午模拟赛,就\(A\)了个\(T1\),\(T2\)炸了我好像就会AT1,真的是啊啊啊看好多人\(200+\),好慌啊下午讲题摸鱼DAY-1MD教练带高一去\(ZZ\)了说:初三的小朋友们不用集训力(捏mm地于是上了一天课......晚上背了几个模板就睡了DAY0上午8:30出......
  • P7072 [CSP-J2020] 直播获奖
    原题链接题解太巧妙了!!code#include<bits/stdc++.h>usingnamespacestd;intmain(){intn,w;cin>>n>>w;intscore[605]={0};for(inti=1;i<=n;i++){intx;cin>>x;score[x]++;intsum......
  • CSP_J2023总结
    维护中include<bits/stdc++.h>usingnamespacestd;intn,ans,k;intmain(){ cin>>n; while(n){ ans++; if(k==0&&n%3==1)k=ans; if(n%3==0)n-=n/3; elsen-=n/3+1; } cout<<ans<<""<<k; return0;}......
  • CSP认证2022.12 452分题解
    A、现值计算题解题目简单易懂,直接写就行了。importmathn,i=map(float,input().split())n=int(n)a=list(map(int,input().split()))ans=0.00forjinrange(n+1):ans=ans+math.pow(1+i,-j)*a[j]print(ans)B、训练计划题解显然是个......
  • 2023 CSP 游记
    目录\(\text{CSP-J}\)游记\(\text{CSP-S}\)游记\(\text{CSP-J}\)游记省流:\(\text{B}\)题挂了\(100\text{pts}\),悲!\(\text{Day-INF}\)初赛\(75.5\)没考过几位大佬。\(\text{悲.jpg}\)\(\text{Day0}\)有点慌,去吃了顿饭,晚上的模拟赛就咕了。怕影响心态,没再......
  • CSP2023 游寄
    前言很难想象,去年一个超越S组一等线50多分的人,这次估分出来比S组一等线低不知道多少分。还好只是初三。虽然但是,CCF确实适合去当心理学家。游记考前晚上也利用起来搞,一到信息课就直接冲向机房,个人认为当我发现自己的问题之后,确实也努力了,只能说时机未到。用一年的职业生涯买......
  • CSP2023 游寄
    你不会T1你会什么题啊,你一题不会你打个锤子啊——老KDay-2最后一场模拟赛,T3被卡常挂了50,T4没读懂题直接爆0。3场模拟赛一崩到底,喜提倒数,寄。Day-1上午动员大会,连线到了lk,真好。然后pty讲了些小技巧,模拟赛中经常因为奇怪错误挂分的我被反复鞭尸。下午和几个巨......
  • CSP-S总结
    时间分配:T1:30min,T3:1.5h,T4:1.5h,剩下交给T2。T1:签到题,秒了。做法:直接枚举密码状态暴力校验。估分:100(话说某人貌似看到我10min开始测样例心态直接爆炸了)T2:感觉难度绿里绿气的,但一直不会。直接写了个区间dp,然后想到枚举左端点向右扩展,用栈维护,拿到50。然后一直感觉栈的......
  • P9755 [CSP-S 2023] 种树 题解
    首先考虑如何求出第\(i\)棵树在\([l,r]\)时间段能长多高。这个东西可以差分一下然后等差数列求和。放一下代码:inlinelllcalc(inti,intx){ if(c[i]>=0){ return(lll)b[i]*x+(lll)c[i]*x*(x+1)/2; }else{ intd=(b[i]-1)/(-c[i]); if(x<=d)return(lll)b[i]*x+(l......