社区讨论
WA 28/56 求助
P6405[COCI 2014/2015 #2] ŠUMA参与者 1已保存回复 0
讨论操作
快速查看讨论及其快照的属性,并进行相关操作。
- 当前回复
- 0 条
- 当前快照
- 1 份
- 快照标识符
- @lo2c6sfc
- 此快照首次捕获于
- 2023/10/23 11:27 2 年前
- 此快照最后确认于
- 2023/11/03 11:35 2 年前
CPP
CPP
#include<bits/stdc++.h>
#define fs(i,x,y,z) for(int i=x;i<=y;i+=z)
#define ft(i,x,y,z) for(int i=x;i>=y;i+=z)
#define int long long
#define ull unsigned long long
#define db double
#define ms(a,b) memset(a,b,sizeof(a))
#define sz(a) sizeof(a)
#define box(x,y) (x-1)*n+y
using namespace std;
const int rw[]={-1,0,1,0,-1,1,-1,1},cl[]={0,1,0,-1,-1,1,1,-1};
const int N=2007,inf=0x3f3f3f3f;
const db eps=1e-12;
inline int read(){
int date=0,w=1;char c=0;
while(c<'0'||c>'9'){if(c=='-')w=-1;c=getchar();}
while(c>='0'&&c<='9'){date=date*10+c-'0';c=getchar();}
return date*w;
}
struct fency{
// int zi,mu;
// const bool operator == (const fency b) const{return zi*b.mu==mu*b.zi;}
db x;
const bool operator == (const fency b) const{return fabs(x-b.x)<=eps;}
const bool operator < (const fency b) const{
// if(1ll*mu*b.mu>0) return 1ll*zi*b.mu<1ll*mu*b.zi;
// else return 1ll*zi*b.mu>1ll*mu*b.zi;
return (b.x-x)>eps;
}//z/m<Z/M,zM<Zm
};
struct edge{
int u,v,nx;
fency w;
const bool operator < (const edge b) const{return w<b.w;}//按照时间排序
}e[N*N*2];
int hd[N],totm;
void add(int u,int v,fency w){
e[++totm].v=v;e[totm].nx=hd[u];
hd[u]=totm;e[totm].w=w;e[totm].u=u;
}
stack<pair<int,int> > s;
int n,h[N][N],v[N][N],fa[N*N],sz[N*N],res,ans;
int find(int x){return fa[x]==x?x:find(fa[x]);}
int find2(int x){return fa[x]==x?x:fa[x]=find2(fa[x]);}
void mrg(int x,int y){
x=find(x),y=find(y);
if(x==y) return;
if(sz[x]>sz[y]) swap(x,y);
fa[x]=y;sz[y]+=sz[x];
res=max(res,sz[y]);
s.push({x,y});
}
signed main(){
n=read();
fs(i,1,n,1) fs(j,1,n,1) h[i][j]=read();
fs(i,1,n,1) fs(j,1,n,1) v[i][j]=read();
fs(i,1,n*n,1) fa[i]=i,sz[i]=1;
fs(i,1,n,1){
fs(j,1,n,1){
fs(k,0,3,1){
int x=i+rw[k],y=j+cl[k];
if(x<1||x>n||y<1||y>n) continue;
if(h[i][j]==h[x][y]&&v[x][y]==v[i][j]) mrg(box(i,j),box(x,y));//万能边合并
}
}
}
fs(i,1,n*n,1) find2(i),ans=max(ans,sz[fa[i]]);res=0;//,don[fa[i]]=sz[fa[i]],ans=max(ans,don[fa[i]]);res=0;
fs(i,1,n,1){
fs(j,1,n,1){
fs(k,0,3,1){
int x=i+rw[k],y=j+cl[k];
if(x<1||x>n||y<1||y>n) continue;
if(fa[box(i,j)]==fa[box(x,y)]) continue;
if(v[i][j]==v[x][y]) continue;//一辈子达不到
if((h[i][j]-h[x][y])*(v[x][y]-v[i][j])<0) continue;
fency p;//p.zi=abs(h[i][j]-h[x][y]);p.mu=abs(v[x][y]-v[i][j]);
p.x=1.0*abs(h[i][j]-h[x][y])/abs(v[x][y]-v[i][j]);
add(fa[box(i,j)],fa[box(x,y)],p);//搜到XY时还会再来一次
}
}
}
// fs(i,1,n*n,1) orifa[i]=fa[i];//清除万能边的影响……?
while(!s.empty()) s.pop();
sort(e+1,e+totm+1);
fs(i,1,totm,1){
if(i!=totm&&e[i].w==e[i+1].w) mrg(e[i].u,e[i].v);//可以合并
else{//结算
mrg(e[i].u,e[i].v);
// if(e[i].w.zi/e[i].w.mu==1) cout<<res<<'?';
ans=max(ans,res);
while(!s.empty()){//逐个删除
pair<int,int> pi=s.top();s.pop();
//X合并到Y
// assert(fa[pi.first]==pi.second);
fa[pi.first]=pi.first;
sz[pi.second]-=sz[pi.first];
}
res=0;
}
}cout<<ans;
return 0;
}
//n 700,所以考虑n^2
//两棵树啥时候相等这个都可以算出来
//对每个时刻测算一次,合并起来即可
//有可能两棵树啥都一样,先给他合并了
//h[i][j]+t*v[i][j]=h[x][y]+t*v[x][y]
//t=(h[x][y]-h[i][j])/(v[i][j]-v[x][y])
/*
4(A) 4 4(A)
4(A) 4 3
6 4 4(A)
*/
fency是一个分数类。若用double实现则分,若用自己写的分数结构体实现则分。struct fency{
int zi,mu;
const bool operator == (const fency b) const{return zi*b.mu==mu*b.zi;}
const bool operator < (const fency b) const{return 1ll*zi*b.mu<1ll*mu*b.zi;}//z/m<Z/M,zM<Zm
};
回复
共 0 条回复,欢迎继续交流。
正在加载回复...