静态 Top Tree

哈哈哈学会的新东西啊,暴搓312行

在此鸣谢机房大蛇QEDQEDQED&&zxkqwq进行一个讲解

前置知识

en。没有。
(可能要理解下线段树的结构,前缀和,二分)

定义

Top Tree是什么?
就是对于一个给定的树,通过compressrake操作,将点和边以及它们维护的信息进行脱水缩合后构成的一棵树。

你可以类比成在树上建一个线段树,及其对应父亲节点维护左右儿子的总信息,这对于单点修改,整体查询问题,是极其方便的。

image

考虑对于左图建一颗Top Tree,每个点就是用来维护每次对应脱水缩合后簇的信息的点。

右图中14这个点维护的是节点5,8以及它们的返祖边(即连接父节点的那条边)形成的簇的信息(也对应下文的compress操作)

右图中12这个点维护的是节点6,7以及它们的返祖边(即连接父节点的那条边)形成的簇的信息(也对应下文的rake操作)

image

Top Tree 中的一个节点有两个儿子(都分别代表一个),这个节点代表的簇是这两个簇通过 Compress 或 Rake 操作合并得到的新簇

我们发现,如果对一个点进行修改,只需要\(O(树高)\)(top tree)的时间复杂度,查询是\(O(1)\)的。

这简直是棒完了!

脱水缩合

en其实人家叫树收缩。(可以类比成线段树的pushup,即将子节点的信息传递到父节点上,方便整体查询)

即上面我们提到的两种妙妙操作

妙妙操作

image

哦其实就是解释一下(原因是肝硬化在我码的时候问询我妙妙操作是什么

compress

将一条长链缩成一条短链

严格来说,即指定一个度数为 \(2\) 的点 \(x\),与点 \(x\) 相邻的那两个点记为 \(y\)\(z\)
我们连一条新边 \(yz\),将点 \(x\)、边 \(xz\)、边 \(xy\) 的信息放到 \(yz\) 中储存,并删去它们

image

rake

将一个二叉树缩成链

严格来说,即将一个度为 \(1\) 的点 \(x\),而且与点 \(x\) 相邻的点 \(y\) 的度数需大于 \(1\),设点 \(y\) 的另一个邻点为 \(z\)
我们将点 \(x\)、边 \(xy\) 的信息放入边 \(yz\) 中储存,并删去它们。

image

我们发现,对于一次树收缩操作,只需要维护对应的合并信息即可(根据例题不同进行灵活调整即可)

我们总是可以通过不断地 rake 一度节点为界点的簇,Compress 一对二度节点为界点的簇,来把整棵树合并成一个大簇。

Tips: Top Tree和普通的二叉树一样拥有相似的结构,所以在进行compressrake操作时要记录父节点,左右儿子节点的标号,方便之后的信息修改。


因为我们把它比作一颗线段树(其结构和维护信息同样也和线段树相仿)

所以我们类比线段树,同样也要明确以下三种操作

建树

建树是保证其时间复杂度正确的关键

以下我们提供一种时间复杂度介于\(O(n)\)\(O(n \log n)\)之间的方法。

暴力建树

只要找到一组满足compressrake操作的点就进行收缩。(这东西树高大抵是\(n\)的,没有人这样建树)

朴素建树

对于一棵树,我们可以将它重链剖分后的所有轻儿子链形成的簇通过rake操作合并到重儿子链上,然后将重儿子链通过compress操作整合成一个簇(对应Top Tree上的某个点)。

我们发现,这种方法的树高有可能被菊花图状物卡成\(n\),则之后的修改操作的时间复杂度就会变成 \(O(n)\),劣完了。

然后考虑优化

优化建树1

我们考虑分治

rake

对于一个有着\(n\)个轻儿子的节点,我们将其进行分治rake
即像二分一样,将\(n\)个儿子分为两组,左组和右组的个数均约为\(n/2\)
一直递归分治,直到某次只有两个儿子,然后进行rake操作,获得新生成的节点信息,然后返回到上一次分组的状态(此时两个儿子的信息已经被储存在了一个节点上),继续上述操作。

image

如图,对于节点\(1\)来说,重儿子链是\(2\)那条链,有\(8\)个轻儿子。
数字对应rake操作的序数,颜色即组内个数(同时发现同种颜色在Top Tree上的层数是相同的)

compress

对于一条有\(n\)个点的链,我们将其进行分治compress
还是如同rake操作一样,将链上的\(n\)个点均分为两组,递归分治进行compress操作。

image

如图,对于\(1\)这条链来说,其中有\(8\)个节点。
数字对应compress操作的序数,颜色即组内个数(同时发现同种颜色在Top Tree上的层数是相同的)

我们发现,这样建图树高最劣是\(O(n \log ^2 n)\)的(咦?怎么和树剖一样啊,我Top Tree 学了个"____"吗?)

然后我们还要优化!

优化建树2

我们通过观察,发现簇的大小是影响操作次数(即树高)的重要因素。当其分治时分成的两组簇的大小越相近,这颗Top Tree就越平均(树高的值就越小)

所以我们在递归分组的时候就不按照\(节点个数/2\)的方式进行分组,而是让每次分成两组的簇大小尽量相等。

rake

即记录子节点的子树大小,找到一个位置使两边子树大小的加和尽量相等。(这里有一个转化,簇的大小为子树大小的加和)

image

如图,黑色边为重儿子链,红色和蓝色的簇就是我们的第一次分组。

compress

还是像rake一样,按照子树大小进行分治。

image

如图,对于重儿子链,红色和蓝色的簇就是我们的第一次分组。

这样,我们就可以建出一颗树高为\(\log n\)Top Tree


总体操作

  • 预处理操作
  1. 将原树进行重链剖分,记录子树大小,重儿子链,并将原树上的一对父子节点的信息用簇记录下来。
  • 轻儿子链形成的簇通过rake操作合并到重儿子链上
  1. 对于其原树上的一个点\(num\),遍历其重儿子链上的所有节点,对于其中一个重儿子节点\(x\),遍历\(x\)的所有轻儿子\(y\),并递归建树。

  2. 递归返回,将轻儿子\(y\)加入到\(x\)的节点集合(此时是轻儿子节点集合)。

  3. 遍历\(x\)节点的轻儿子集合,将其子树大小以前缀和的方式存储(方便之后找到总子树大小的分界点)。

  4. 递归进行分治rake操作,对于一次递归,对于其左端点\(l\)和右端点\(r\),使用二分查找找到分界点 \(mid\)(满足两边子树大小的加和尽量相等)。继续递归并回退然后执行rake即可。

  • 将重儿子链通过compress操作整合成一个簇
  1. 回到我们的\(num\)节点,遍历其重儿子\(x\),并加入到\(num\)的节点集合(此时是重儿子节点集合)。

  2. 遍历\(num\)节点的重儿子集合,将其子树大小以前缀和的方式存储(方便之后找到总子树大小的分界点)。

  3. 递归进行分治compress操作,对于一次递归,对于其左端点\(l\)和右端点\(r\),使用二分查找找到分界点 \(mid\)(满足两边子树大小的加和尽量相等)。继续递归并回退然后执行compress即可。

  • end
  1. 清空\(num\)的连边,只记录与其父亲的连边。(为之后的建树做处理)

修改

我们在建树预处理的时候记录了有关一对父子节点信息的簇,同时,我们记录对于该子节点Top Tree上对应的点的标号。

为什么是子节点?
因为我们维护的这个簇上界点是父亲节点,下界点是儿子节点;
而簇维护的信息“包下不包上”,这样我们才能进行合理的信息转移以及维护。
所以该簇对应的节点是儿子节点。

然后直接在对应的Top Tree上的点进行修改。

若该点的类型是C,即这个节点是由它的左右儿子节点维护的簇通过compress操作构成的,就再次进行compress操作更新这个节点维护的信息。(和线段树的pushup类似)

反之,若该点的类型是R,即这个节点是由它的左右儿子节点维护的簇通过rake操作构成的,就再次进行rake操作更新这个节点维护的信息。(和线段树的pushup类似)

然后找到这个节点在Top Tree上的父节点,递归更新即可。

查询

整体查询就直接查询Top Tree根节点所维护的信息即可。

(是的就是这样)

啊终于终于写完了!!

接下来让我们看一道例题

例题

luogu P4115 Qtree4

P4115 Qtree4

题目描述

给出一棵边带权的节点数量为 \(n\) 的树,初始树上所有节点都是白色。有两种操作:

  • C x,改变节点 \(x\) 的颜色,即白变黑,黑变白。

  • A,询问树中最远的两个白色节点的距离,这两个白色节点可以重合(此时距离为 \(0\))。

输入格式

第一行,输入一个正整数 \(n\ (n \le {10}^5\))。

接下来 \(n-1\) 行,每行有 \(3\) 个整数 \(a,b,c\),代表节点 \(a\) 和节点 \(b\) 之间连一条边权为 \(c\ (|c|\le{10}^3)\) 的边。

接下来一行,一个正整数 \(q\ (q\le 2\times 10^5)\),表示操作的数量。

接下来 \(q\) 行,每行一次操作。

输出格式

对于每次 A 操作,如果树上不存在白点,输出一行一个字符串 They have disappeared.,否则输出一行一个整数代表树上最远的两个白色节点的距离。

输入输出样例 #1

输入 #1

3
1 2 1
1 3 1
7
A
C 1
A
C 2
A
C 3
A

输出 #1

2
2
0
They have disappeared.

分析题目

分析题目,我们发现是树上问题+单点修改+整体查询,十分鱼块啊!直接上\(Top Tree\)

建树,修改,查询是十分板板的(甚至可以Ctrl+C Ctrl+V的)

然后考虑我们两个妙妙操作要维护什么信息

这题让我们求对于这颗原树中两个白点的最远距离

对于一个簇来说,我们要附加维护四个值(除簇的类型,父节点,左右儿子节点,上界点,下界点,节点标号外)

  1. \(mx\)
    簇内两个白点之间的最远距离

  2. \(mu\)
    上界点到簇内一个白点的最远距离

  3. \(md\)
    下界点到簇内一个白点的最远距离

  4. \(dis\)
    上界点到下界点的距离


  • 初始化信息
    因为是求最大值,所以

\[mx=mu=md=-\infty \]

\(dis\)的定义即上界点和下界点之间的距离

对于原树上一对父子节点形成的簇来说

\[dis=两点之间的边权 \]

而对于其他的簇来说:

compress操作

\[dis=dis_{左儿子}+dis_{右儿子} \]

rake操作

\[dis=dis_{右儿子} \]


考虑转移

当前节点维护的是\(x\)\(y\)两个簇合并的信息。

对于compress操作来说

此时左儿子\(x\)是包含当前节点的上界点的簇,右儿子\(y\)是包含当前节点的下界点的簇。


\(x\)的上界点是当前节点的上界点。
\(x\)的下界点是\(y\)的上界点。
\(y\)的下界点是当前节点的下界点。

对于rake操作来说

此时左儿子\(x\)是要合并在\(y\)上的一个簇,右儿子\(y\)是包含当前节点的上下界点的簇。

\(y\)的上界点是当前节点的上界点。
\(x\)的下界点和上界点被合并在簇内。
\(y\)的下界点是当前节点的下界点。


对于\(x\)这个簇的下界点是白点的情况,有一些附加转移。

可以自己先思考一下,实在不会转移可以参考代码

代码实现


#include<bits/stdc++.h>
using namespace std;
const long long inf=1e14;
struct jade
{long long x,y;//上,下界点 long long mx,mu,md;//簇中答案,上界点到簇中白点的最大距离,下界点到簇中白点的最大距离 long long id;//标号 long long dis;//上下界点距离 char type;//该点的类型 
}clus[200010];//top tree 
long long n,m;
long long col[200010];//点的颜色 
long long pos[200010],fa[200010],ls[200010],rs[200010];//(新建节点时)原树上的点对应toptree的点标号,toptree上的父节点,左子节点,右子节点标号 
long long root=1;//toptree的根 
long long h[200010],to[400010],nxt[400010],v[400010],tot;//链式前向星存图 
long long posfa[200010];//原树上的点对应toptree的点标号 
long long da[200010],son[200010],siz[200010],cnt;// 原树上的父节点,重儿子节点,子树大小,toptree点的个数 
long long sum;//黑点的个数(判无解 
vector <long long> heavy[200010];//对于i节点的重儿子链 
vector <long long> node[200010];//i节点的儿子集 
vector <long long> sizsum[200010];//i节点儿子的子树前缀和 
void add(long long x,long long y,long long val)//建边 
{tot++;to[tot]=y;nxt[tot]=h[x];h[x]=tot;v[tot]=val;
}
void compress(jade x,jade y,jade &res)//将一条链缩短 
{res.mx=res.mu=res.md=-inf;res.x=x.x;res.y=y.y;res.dis=x.dis+y.dis;res.mx=max({x.md+y.mu,x.mx,y.mx});res.mu=max(x.mu,y.mu+x.dis);res.md=max(x.md+y.dis,y.md);if(col[x.y]==0){res.mx=max({res.mx,x.md,y.mu,0*1ll});res.mu=max(res.mu,x.dis);res.md=max(res.md,y.dis);}pos[x.y]=res.id;fa[x.id]=fa[y.id]=res.id;ls[res.id]=x.id;rs[res.id]=y.id;res.type='C';root=res.id;
}
void rake(jade x,jade y,jade &res)//将叉数减一 
{res.mx=res.mu=res.md=-inf;res.x=y.x;res.y=y.y;res.dis=y.dis;res.mx=max({x.mx,y.mx,x.mu+y.mu});res.mu=max(x.mu,y.mu);res.md=max(x.mu+y.dis,y.md);if(col[x.y]==0){res.mx=max({res.mx,x.md,y.mu+x.dis,0*1ll});res.mu=max(res.mu,x.dis);res.md=max(res.md,x.dis+y.dis);}pos[x.y]=res.id;fa[x.id]=fa[y.id]=res.id;ls[res.id]=x.id;rs[res.id]=y.id;res.type='R';root=res.id;
}
void update(long long x)//修改 
{if(x==0)//边界 {return ;}if(clus[x].type=='C'){compress(clus[ls[x]],clus[rs[x]],clus[x]);update(fa[x]);//递归修改 }else{rake(clus[ls[x]],clus[rs[x]],clus[x]);update(fa[x]);}
}
void dfs1(long long x)
{siz[x]=1;for(long long i=h[x];i;i=nxt[i]){long long y=to[i];if(y==da[x]){continue;}da[y]=x;cnt++;//初始化 posfa[y]=cnt;clus[cnt].x=x;clus[cnt].y=y;clus[cnt].id=cnt;clus[cnt].dis=v[i];clus[cnt].mx=clus[cnt].mu=clus[cnt].md=-inf;dfs1(y);if(siz[y]>siz[son[x]]){son[x]=y;}siz[x]+=siz[y];}
}
void dfs2(long long x,long long top)
{heavy[top].push_back(x);if(son[x]!=0){dfs2(son[x],top);}for(long long i=h[x];i;i=nxt[i]){long long y=to[i];if(y==da[x]||y==son[x]){continue;}dfs2(y,y);}
}
long long solve_compress(long long l,long long r,long long x) 
{//compress递归缩树 if(l>r){return 0;}if(l==r){return posfa[node[x][l]];}long long ll=l,rr=r;while(ll+1<rr)//二分查找分界点 {long long mid=(ll+rr)>>1;if((sizsum[x][mid]-sizsum[x][l-1])*2<=(sizsum[x][r]-sizsum[x][l-1])){ll=mid;}else{rr=mid;}}long long mid=ll;long long lson=solve_compress(l,mid,x);long long rson=solve_compress(mid+1,r,x);cnt++;long long res=cnt;clus[cnt].id=cnt;compress(clus[lson],clus[rson],clus[res]);//合并左右儿子信息 return res;
}
long long solve_rake(long long l,long long r,long long x)
{//rake递归缩树if(l>r){return 0;}if(l==r){return posfa[node[x][l]];}long long ll=l,rr=r;while(ll+1<rr)//二分查找分界点{long long mid=(ll+rr)>>1;if((sizsum[x][mid]-sizsum[x][l-1])*2<=(sizsum[x][r]-sizsum[x][l-1])){ll=mid;}else{rr=mid;}}long long mid=ll;long long lson=solve_rake(l,mid,x);long long rson=solve_rake(mid+1,r,x);cnt++;long long res=cnt;clus[cnt].id=cnt;rake(clus[lson],clus[rson],clus[res]);//合并左右儿子信息 return res;
}
void build(long long num)//建树 
{for(long long x:heavy[num])//遍历重儿子链 {if(son[x]==0){continue;}sizsum[x].push_back(0);node[x].push_back(0);for(long long i=h[x];i;i=nxt[i])//遍历重儿子上的轻儿子 {long long y=to[i];if(y!=son[x]&&y!=da[x]){build(y);node[x].push_back(y);//此时是轻儿子集 }}for(long long i=1;i<node[x].size();i++)//求前缀和 {sizsum[x].push_back(sizsum[x][i-1]+siz[node[x][i]]);}long long ro=solve_rake(1,node[x].size()-1,x);//递归建树 if(ro!=0)//有新点 {cnt++;clus[cnt].id=cnt;rake(clus[ro],clus[posfa[son[x]]],clus[cnt]);posfa[son[x]]=cnt;}}sizsum[num].clear();//清除历史遗留问题 node[num].clear();sizsum[num].push_back(0);node[num].push_back(0);for(long long x:heavy[num]){node[num].push_back(x);//此时变成重儿子集 }for(long long i=1;i<node[num].size();i++)//求前缀和 {sizsum[num].push_back(sizsum[num][i-1]+siz[da[node[num][i]]]-siz[node[num][i]]);}if(num!=1)//不是原树上的根节点 {posfa[num]=solve_compress(1,node[num].size()-1,num);}else{posfa[num]=solve_compress(2,node[num].size()-1,num);}h[num]=0;//清空 add(num,da[num],0);return ;
}
int main()
{ios::sync_with_stdio(0);cin.tie(0);cout.tie(0);cin>>n;for(long long i=1;i<n;i++){long long x,y,val;cin>>x>>y>>val;add(x,y,val);add(y,x,val);}cin>>m;dfs1(1);//预处理一对父子节点簇,子树大小,重儿子 dfs2(1,1);//预处理重儿子链 build(1);//递归建树 while(m--){char op;cin>>op;if(op=='C'){long long x;cin>>x;sum-=col[x];col[x]^=1;sum+=col[x];update(pos[x]);//修改 }else{//查询 if(sum<n){long long ans=clus[root].mx;if(col[clus[root].x]==0){ans=max({ans,0*1ll,clus[root].mu});}if(col[clus[root].y]==0){ans=max({ans,0*1ll,clus[root].md});}if(col[clus[root].x]==0&&col[clus[root].y]==0){ans=max({ans,0*1ll,clus[root].dis});}cout<<ans<<'\n';}else//无解 {cout<<"They have disappeared.\n";}}}return 0;
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/1206678.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【笔记】【周期】

目录 《周期》核心解读笔记 第一类:基本面周期 —— 经济、政府、企业的底层逻辑 1. 经济周期 2. 政府调节周期 3. 企业盈利周期 第二类:心理周期 —— 投资人的情绪钟摆 1. 心理钟摆 2. 风险态度周期 第三类:市场周期 —— 信贷、房地产、股市的具体玩法 1. 信贷…

typescript-类的访问权限public、private、protected

访问权限这个你可以理解为类的某个属性或者某个方法可以在哪里访问。分三种&#xff0c;public(默认),protected,privatepublicpublic表示在任意的地方都可以访问某个类的属性或者方法。场景&#xff1a;比如你叫小名&#xff0c;别人要叫你的时候&#xff0c;得知道你的名字&a…

【笔记】【逆向思维:顶级大脑的降维思考智慧】

目录 逆向思维:顶级大脑的降维思考智慧 方法一:反向目标法 —— 从 “要什么” 到 “不要什么” 方法二:因果倒置法 —— 从 “结果推原因” 到 “原因推反向结果” 方法三:换位思考法 —— 从 “我的视角” 到 “对立面视角” 误区一:为了反向而反向,忽略底层逻辑 …

工信部擘画“开源新基建”:推动工业互联网平台生态跃迁

当工业的庞大躯干寻求智能化的灵魂&#xff0c;一场围绕“连接”与“控制”的深层博弈正在展开。开源&#xff0c;这把曾经重塑了互联网世界的钥匙&#xff0c;如今被赋予了打开工业互联网下一道价值之门的使命。1月13日&#xff0c;中华人民共和国工业和信息化部&#xff08;以…

ASTM D4169-23e1测试,ASTM D4169标准模拟,包装运输测试ASTM D4169试验

一、标准定义与合规性确认 ASTM D4169-23e1 是美国材料与试验协会&#xff08;ASTM International&#xff09;发布的《运输集装箱和系统性能测试的标准实施规程》&#xff0c;2023 年 12 月批准、2024 年 1 月发布&#xff0c;核心是通过实验室模拟物流全链路风险&#xff0c…

【课程设计/毕业设计】基于SpringBoot的医院医疗护工陪护系统的设计与实现基于springboot的护工管理便捷服务系统【附源码、数据库、万字文档】

博主介绍&#xff1a;✌️码农一枚 &#xff0c;专注于大学生项目实战开发、讲解和毕业&#x1f6a2;文撰写修改等。全栈领域优质创作者&#xff0c;博客之星、掘金/华为云/阿里云/InfoQ等平台优质作者、专注于Java、小程序技术领域和毕业项目实战 ✌️技术范围&#xff1a;&am…

中国AI模型的“双向涟漪”——从全球南方自主到美企的市场转向

美国闭源AI模型长期以“技术垄断地缘绑定”主导全球市场&#xff0c;中国开源人工智能模型则以“自主可控、成本友好、适配本地”为核心优势&#xff0c;逐步渗透全球南方国家、发达国家企业及硅谷核心圈&#xff0c;推动全球AI技术选择格局发生深刻变革。据彭博社、英国《金融…

SRM+AI智能寻源:10分钟搞定供应商寻源!

对于采购人员而言&#xff0c;寻源是采购非常重要&#xff0c;但同时也非常耗费精力的环节。传统模式下&#xff0c;为找到合适的供应商&#xff0c;采购人员可能需要&#xff1a;通过搜索引擎大量检索、搜集各类供应商信息&#xff0c;筛选符合要求的供应商。逐一在征信平台上…

Java计算机毕设之基于Springboot的医疗护理管理服务系统(完整前后端代码+说明文档+LW,调试定制等)

博主介绍&#xff1a;✌️码农一枚 &#xff0c;专注于大学生项目实战开发、讲解和毕业&#x1f6a2;文撰写修改等。全栈领域优质创作者&#xff0c;博客之星、掘金/华为云/阿里云/InfoQ等平台优质作者、专注于Java、小程序技术领域和毕业项目实战 ✌️技术范围&#xff1a;&am…

强烈安利8个AI论文网站,本科生搞定毕业论文不求人!

强烈安利8个AI论文网站&#xff0c;本科生搞定毕业论文不求人&#xff01; 论文写作不再难&#xff0c;AI 工具助你轻松应对 对于很多本科生来说&#xff0c;毕业论文是一项既重要又棘手的任务。从选题到撰写&#xff0c;再到修改和降重&#xff0c;每一步都充满了挑战。而如今…

firebird 数据库 C# 开发报错

1、找不到dllUnable to load DLL fbembed or one of its dependencies: 找不到指定的模块。 (0x8007007E) 2、磁盘结构错误发现式12 不支持13的错误 firebird下载的exe选择3的版本。不要选5的版本。 3、占用,多个程…

企业邮箱收费吗?解析主流品牌的三种收费模式

在企业数字化转型的进程中&#xff0c;专业的企业邮箱已成为标配工具。许多初创团队和企业在初次接触时&#xff0c;常会疑惑&#xff1a;“企业邮箱收费吗&#xff1f;” 答案是肯定的。与个人免费邮箱不同&#xff0c;专业的企业邮箱服务通常需要付费&#xff0c;以获得专属域…

PCB行业MES厂商TOP3推荐:主流厂商对比与务实建议

在智能制造深入推进的背景下&#xff0c;MES系统已成为PCB企业提升效率、保障质量、满足客户追溯要求的关键基础设施。然而&#xff0c;PCB制造具有工序繁多&#xff08;20道&#xff09;、产品高度非标&#xff08;HDI/FPC/厚铜板等&#xff09;、质量敏感度高、交付节奏快等特…

PCB板上你是普通油墨,我是低损耗油墨,能一样吗?

一博高速先生成员--黄刚 文章一开始就先给各位选择困难症的粉丝们出一道题&#xff0c;如果今天让你们来设计下面的这组25G光口信号的布线&#xff0c;你会选择走内层还是表层呢&#xff1f; 其实高速先生相信在座的各位PCB工程师更愿意选择走表层&#xff0c;原因就是过孔如果…

重组蛋白表达系统技术详解:从原核到真核的系统比较与选择指南

重组蛋白表达系统是现代生命科学研究和生物技术服务行业的基础性技术平台。从科研试剂的角度,重组蛋白表达系统不仅支撑着基础研究、药物靶标验证、抗体筛选等多种实验,还为生物公司提供了稳定、可控的蛋白样品来源。…

针对工科论文或材料密集型研究,以下工具能有效优化AIGC检测结果,同时保持学术严谨性

pre { white-space: pre !important; word-wrap: normal !important; overflow-x: auto !important; display: block !important; font-family: "Consolas", "Monaco", "Courier New", …

FastAPI系列(03):路径操作装饰器方法及其参数

本系列汇总,请查看这里:https://www.cnblogs.com/uncleyong/p/19503695 路径操作装饰器方法 也就是请求方式,fastapi支持各种请求方式:@app.get() @app.post() @app.put() @app.patch() @app.delete() @app.option…

快捷支付:高效应对高频交易痛点

针对高价商品交易中易出现的付款失败、收款受限等问题&#xff0c;快捷支付可轻松应对&#xff0c;支持一分钟内完成上百笔交易&#xff0c;完美适配高并发交易场景。操作流程极简高效&#xff1a;用户首次绑卡仅需提交银行卡号、开户名、预留手机号三要素&#xff1b;后续付款…

市场规模超千亿,银发客群成新宠!益生菌开启中老年大健康赛道下一风口?

​银发族健康管理&#xff0c;深入至体内菌群微生态作者 | AgeClub任子勋前言2025年国内益生菌赛道呈高速增长。魔镜数据显示&#xff0c;2025年前七个月&#xff0c;益生菌市场总销售额达到704.36亿元&#xff0c;同比增长39.75%&#xff0c;销量同比增长25.47%。在社会老龄化…

【计算机毕业设计案例】基于springboot的康复医院护工管理平台护工管理便捷服务系统(程序+文档+讲解+定制)

博主介绍&#xff1a;✌️码农一枚 &#xff0c;专注于大学生项目实战开发、讲解和毕业&#x1f6a2;文撰写修改等。全栈领域优质创作者&#xff0c;博客之星、掘金/华为云/阿里云/InfoQ等平台优质作者、专注于Java、小程序技术领域和毕业项目实战 ✌️技术范围&#xff1a;&am…