日常刷题2025-3-21
1.日常刷题2025-3-222.日常训练2025-1-23.日常训练2025-1-34.日常训练2025-1-55.日常训练2025-1-86.日常训练2025-1-117.日常训练2025-1-128.日常训练2025-1-139.日常训练2025-1-1410.日常训练2025-1-1511.日常训练2025-1-1612.日常训练2025-1-1713.日常训练2025-1-1814.日常训练2025-1-1915.日常训练2025-1-2116.日常训练2025-1-2217.日常刷题2025-1-2318.日常训练2025-1-2419.日常刷题2025-1-2520.日常刷题21.日常刷题2025-2-622.日常刷题2025-2-923.日常刷题2025-2-1424.日常刷题2025-2-1525.日常刷题2025-2-1726.日常刷题2025-2-2027.日常刷题2025-2-2128.日常刷题2025-2-2229.日常刷题2025-2-2430.日常刷题2025-2-2631.日常刷题2025-2-2732.日常刷题2025-2-2833.日常刷题2025-3-134.日常刷题2025-3-235.日常刷题2025-3-336.日常刷题2025-3-537.日常刷题2025-3-638.日常刷题2025-3-739.日常刷题2025-3-840.日常刷题2025-3-941.日常刷题2025-3-1042.日常刷题2023-3-1143.日常刷题2025-3-1344.非常棒的二分和DP45.日常刷题2025-3-1646.日常刷题2025-3-18
47.日常刷题2025-3-21
日常刷题2025-3-21
D. Tree Jumps
rating:1600
思路:方案数DP
看到求方案数,就先给DP预定好位置。分析一下题意,发现一个节点的方案数会来自它父亲的兄弟节点的方案数,所以我们只要从上往下,当求下面层的方案数时上一层的方案数已经求出来了。所以就是DP
代码
#include <bits/stdc++.h> using u64 = unsigned long long; using i64 = long long; typedef std::pair<int, int> pii; const int N = 1e5+5; template<typename T> T power(T a, i64 b) { T ret = 1; while (b) { if (b & 1) ret = ret * a; a = a * a; b >>= 1; } return ret; } template<int P> struct ModInt { int val; static inline int norm(int x) { if (x < 0) x += P; if (x >= P) x -= P; return x; } ModInt operator - () const { return ModInt(P - val); } inline ModInt inv() const { return power(*this, P - 2); } ModInt() {} ModInt(int val) : val(norm(val % P)) {} ModInt(i64 val) : val(norm(val % P)) {} bool constexpr operator < (const ModInt &rhs) const { return val < rhs.val; } bool constexpr operator == (const ModInt &rhs) const { return val == rhs.val; } bool constexpr operator != (const ModInt &rhs) const { return val != rhs.val; } ModInt &operator += (const ModInt &rhs) & { return val = norm(val + rhs.val), *this; } ModInt &operator -= (const ModInt &rhs) & { return val = norm(val - rhs.val), *this; } ModInt &operator *= (const ModInt &rhs) & { return val = 1ll * val * rhs.val % P, *this; } ModInt &operator /= (const ModInt &rhs) & { return *this *= rhs.inv(); } ModInt constexpr operator + (const ModInt &rhs) const { ModInt ret = *this; return ret += rhs; } ModInt constexpr operator - (const ModInt &rhs) const { ModInt ret = *this; return ret -= rhs; } ModInt constexpr operator * (const ModInt &rhs) const { ModInt ret = *this; return ret *= rhs; } ModInt constexpr operator / (const ModInt &rhs) const { ModInt ret = *this; return ret /= rhs; } friend std::istream& operator >> (std::istream& is, ModInt &rhs) { i64 val; is >> val; return rhs.val = norm(val % P), is; } friend constexpr std::ostream& operator << (std::ostream& os, const ModInt &rhs) { return os << rhs.val; } }; const int M = 998244353; using Z = ModInt<M>; void solve(){ int n; std::cin>>n; std::vector<std::vector<int>> d(n); std::vector<int> fa(n); fa[0]=-1; std::vector<int> l(n); l[0]=0; for(int i=1,x;i<n;i++){ std::cin>>x; x--; fa[i]=x; l[i]=l[x]+1; d[x].push_back(i); } std::vector<int> p(n); std::iota(p.begin(),p.end(),0); std::sort(p.begin(),p.end(),[&](int x,int y){ return l[x]<l[y]; }); std::vector<Z> f(n); std::vector<Z> laysum(n,0); for(int x:p){ if(x==0||fa[x]==0){ f[x]=1; laysum[l[x]]+=1; }else{ f[x]=laysum[l[x]-1]-f[fa[x]]; laysum[l[x]]+=f[x]; } } Z res=0; for(auto x:f) res+=x; std::cout<<res<<'\n'; } signed main(){ std::ios::sync_with_stdio(false); std::cin.tie(nullptr); std::cout<<std::setiosflags(std::ios::fixed)<<std::setprecision(15); int t = 1, i; std::cin >> t; for (i = 0; i < t; i++){ solve(); } return 0; }
智乃的“凑数”题(Easy Version)
思路:双重01背包
一道不错的背包题。
代码
#include <bits/stdc++.h> using u64 = unsigned long long; using i64 = long long; typedef std::pair<int, int> pii; const int mod = 998244353; const int N = 105; int n,m,a[N]; int dp[N][N],pre[N][N]; void query(int q){ for(int i=1;i<=ceil(sqrt(q));i++){ if(q%i!=0)continue; if(dp[i][q/i]){ std::vector<int> vx,vy; int x=i,y=q/i; while(x!=0||y!=0){ if(pre[x][y]>0){ vx.push_back(pre[x][y]); x-=pre[x][y]; }else{ vy.push_back(pre[x][y]*(-1)); y+=pre[x][y]; } } std::cout<<"Yes\n"; std::cout<<vx.size()<<' '<<vy.size()<<'\n'; for(auto e:vx) std::cout<<e<<' '; std::cout<<'\n'; for(auto e:vy) std::cout<<e<<' '; std::cout<<'\n'; return; } } std::cout<<"No\n"; } void solve(){ dp[0][0]=1; std::cin>>n>>m; for(int i=1;i<=n;i++)std::cin>>a[i]; for(int i=1;i<=n;i++){ for(int x=100;x>=0;x--){ for(int y=100;y>=0;y--){ if(dp[x][y])continue; if(x>=a[i]&&dp[x-a[i]][y]){ dp[x][y]=1; pre[x][y]=a[i]; }else if(y>=a[i]&&dp[x][y-a[i]]){ dp[x][y]=1; pre[x][y]=a[i]*(-1); } } } } while(m--){ int x;std::cin>>x; query(x); } } signed main(){ std::ios::sync_with_stdio(false); std::cin.tie(nullptr); std::cout<<std::setiosflags(std::ios::fixed)<<std::setprecision(15); int t = 1, i; for (i = 0; i < t; i++){ solve(); } return 0; }
本文作者:califeee
本文链接:https://www.cnblogs.com/califeee/p/18785217
版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 2.5 中国大陆许可协议进行许可。
【推荐】还在用 ECharts 开发大屏?试试这款永久免费的开源 BI 工具!
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步