11.6模拟赛

来源:互联网 发布:魔兽世界70数据库 编辑:程序博客网 时间:2024/06/05 21:53

补坑,这套题太难了= =
t3看都不想看了果断弃疗,这套题思维难度直逼省选,第一题一看见最大的最小值就往二分答案上考虑,首先这道题给了一个矩形,二分答案之后就变成一个01矩阵,然后此题就变成了O(n*m*log(maxw[i])),百分之百的数据范围是10的10次方,除非数据故意卡你否则绝对能过(其实数据卡你也不一定会T)。
附上代码

#include<cstdio>#include<iostream>#include<algorithm>#include<cstring>#include<string>using namespace std;long long int map[1010][1010],a[1010][1010],s[1010],n,m,tim,l,r;int check(long long int x){    tim++;    for (int i=1;i<=n;i++)    {        int st=0;        for (int j=1;j<=m;j++)if (a[i][j]>=x)s[++st]=j;        for (int j=1;j<st;j++)        for (int k=j+1;k<=st;k++)//转换为01矩阵。        {            if (map[s[j]][s[k]]==tim)return 1;            map[s[j]][s[k]]=tim;        }    }    return 0;}int main(){    freopen("build.in","r",stdin);    freopen("build.out","w",stdout);    cin>>n>>m;    for (int i=1;i<=n;i++)    for (int j=1;j<=m;j++)    {        scanf("%I64d",&a[i][j]);        if (r<a[i][j])r=a[i][j];    }    for ( long long int x;l<r;(check(x=l+r+1>>1))?l=x:r=x-1);//二分答案    printf("%I64d",l);    fclose(stdin);    fclose(stdout);    return 0;   }

第二题也是难啊,是洛谷的P1613跑路,看到2的k次方就应该想到倍增的QAQ,还是这类题目做少了,以后要注意读题= =,其实就是一个倍增问题,一开始先初始化使每两点的距离为INF(其实就是floyd的正常套路啦),然后枚举每个点判断两个点能否用1s到达,如果可以就将两点连上一条边,之后用floyd来处理一遍处理出来每两点之间的距离,从而得出第一个点与第n个点之间的距离,其实代码比较好写,但是思维难度略大。
附代码

#include<cstdio>#include<iostream>#define rep(i,x) for (register int i=1;i<=x;i++)using namespace std; int d[60][60],n,m,f[40][60][60],u,v;int main(){    freopen("run.in","r",stdin);    freopen("run.out","w",stdout);    cin>>n>>m;    rep(i,n)rep(j,n)d[i][j]=1<<28;//预处理    rep(i,m)    {        scanf("%d%d",&u,&v);        f[0][u][v]=d[u][v]=1;//读边,初始化距离为1的点    }    rep(k,31)rep(l,n)rep(i,n)rep(j,n)    {        if (f[k-1][l][j]+f[k-1][i][l]==2)f[k][i][j]=d[i][j]=1;//处理能够在1s之内到达点    }    rep(k,n)rep(i,n)rep(j,n)    if (d[i][k]+d[k][j]<d[i][j])    d[i][j]=d[i][k]+d[k][j];//floyd处理一遍    cout<<d[1][n];//输出答案    fclose(stdin);    fclose(stdout);    return 0;}
0 0
原创粉丝点击