W3 school 菜鸟教程 我要自学网 信息学奥赛NOI 花哥的博客 不逼自己一把,怎知自己有多优秀——校长语录

一本通网站练习目录及AC代码(基础篇己完结)

信息学奥赛一本通

第一部分:C++语言

第一章 C++语言入门

1000:入门测试题目

#include<iostream>
using namespace std;

int main()
{
    int a,b;
    cin>>a>>b;
    cout<<a+b;
    return 0;
}
点击查看AC代码 

1001:Hello,World!

#include<iostream>
using namespace std;

int main()
{
    cout<<"Hello,World!";
     return 0;
}
点击查看AC代码

1002:输出第二个整数

#include<iostream>
using namespace std;

int main()
{
    int a,b,c;
    cin>>a>>b>>c;
    cout<<b;     
     return 0;
}
点击查看AC代码

1003:对齐输出

#include<iostream>
#include<bits/stdc++.h>
using namespace std;

int main()
{
    int a,b,c;
    cin>>a>>b>>c;
    cout<<fixed<<setw(8)<<a<<' ';
    cout<<fixed<<setw(8)<<b<<' ';
    cout<<fixed<<setw(8)<<c;
    return 0;
}
点击查看AC代码

1004:字符三角形

#include<iostream>
using namespace std;

int main()
{
    char ch;
    cin>>ch;
    cout<<"  "<<ch<<'\n';
    cout<<" "<<ch<<ch<<ch<<'\n';
    cout<<ch<<ch<<ch<<ch<<ch<<'\n'; 
     return 0;
}
点击查看AC代码

1005:地球人口承载力估计

#include<cstdio>
int main(){
    int a,b,x,y;
    double z;
    scanf("%d %d %d %d",&x,&a,&y,&b);
    z=(a*x-b*y)/(a-b);
    printf("%.2f",z);
    return 0;
}
点击查看AC代码

第二章 顺序结构程序设计

第一节 运算符和表达式

1006:A+B问题

#include<iostream>
using namespace std;

int main()
{
    int a,b;
    cin>>a>>b;
    cout<<a+b;
    return 0;
}
点击查看AC代码

1007:计算(a+b)×c的值

#include<iostream>
using namespace std;

int main(){
    int a,b,c;
    cin>>a>>b>>c;
    cout<<(a+b)*c<<endl; 
    return 0;
}
点击查看AC代码

1008:计算(a+b)/c的值

#include<iostream>
using namespace std;

int main()
{
    int a,b,c;
    cin>>a>>b>>c;
    cout<<(a+b)/c; 
     return 0;
}
点击查看AC代码

1009:带余除法

#include<iostream>
using namespace std;

int main()
{
    int bcs,cs,s,ys;
    cin>>bcs>>cs;
    s=bcs/cs;
    ys=bcs%cs;
    cout<<s<<' '<<ys;
    return 0;
}
点击查看AC代码

1010:计算分数的浮点数值

#include<iostream>
#include<iomanip>
using namespace std;

int main()
{
    double a,b;
    cin>>a>>b;
    cout<<fixed<<setprecision(9)<<a/b;
     return 0;
}
点击查看AC代码

第二节 常量和变量

1011:甲流疫情死亡率

#include<iostream>
 #include<iomanip>
using namespace std;

int main(){
    int a,b;
    cin>>a>>b;
    cout<<fixed<<setprecision(3)<<100.0*b/a<<'%'<<endl;
    return 0;
}
点击查看AC代码

1012:计算多项式的值

#include<iostream>
#include<iomanip>
using namespace std;

int main(){
    double x,a,b,c,d;
    cin>>x>>a>>b>>c>>d;
    cout<<fixed<<setprecision(7)<<x*(x*(a*x+b)+c)+d;
    return 0;
}
点击查看AC代码

1013:温度表达转化

#include<iostream>
#include<iomanip>
using namespace std;

int main(){
    double f;
    cin>>f;
    cout<<fixed<<setprecision(5)<<(f-32)/9*5;
    return 0;
}
点击查看AC代码

1014:与圆相关的计算

#include<iostream>
using namespace std;
#include<iomanip>
int main()
{
    double r,pi=3.14159,d,c,s;
    cin>>r;
    d=r*2;
    c=pi*2*r;
    s=pi*r*r;
    cout<<fixed<<setprecision(4)<<d;
    cout<<' '<<fixed<<setprecision(4)<<c;
    cout<<' '<<fixed<<setprecision(4)<<s;
     return 0;
}
点击查看AC代码

1015:计算并联电阻的阻值

#include<iostream>
using namespace std;
#include<iomanip> //
int main(){
    float r1,r2;
    cin>>r1>>r2;
    cout<<fixed<<setprecision(2)<<r1*r2/(r1+r2); 
    return 0;
}
点击查看AC代码

第三节 标准数据类型

1016:整型数据类型存储空间大小

#include<iostream>
using namespace std;
//#include<iomanip> fixed<<setprecision
int main(){
    cout<<sizeof(int)<<' '<<sizeof(short)<<endl;
    return 0;
}
点击查看AC代码

1017:浮点型数据类型存储空间大小

#include<iostream>
using namespace std;
//#include<iomanip> fixed<<setprecision
int main(){
    cout<<sizeof(float)<<' '<<sizeof(double)<<endl;
    return 0;
}
点击查看AC代码

1018:其他数据类型存储空间大小

#include<iostream>
using namespace std;
//#include<iomanip> fixed<<setprecision
int main(){
    cout<<sizeof(bool)<<' '<<sizeof(char)<<endl;
    return 0;
}
点击查看AC代码

1019:浮点数向零舍入

#include<iostream>
using namespace std;
//#include<iomanip> fixed<<setprecision
int main(){
    float a;
    int b;
    cin>>a;
    b=int(a);
    cout<<b<<endl;
    return 0;
}
点击查看AC代码

1020:打印ASCII码

#include<iostream>
using namespace std;
//#include<iomanip> fixed<<setprecision
int main(){
    char ch;
    cin>>ch;
    cout<<ch+0<<endl;
    return 0;
}
点击查看AC代码

1021:打印字符

#include<iostream>
using namespace std;
//#include<iomanip> fixed<<setprecision
int main(){
    int n;
    cin>>n;
    cout<<char(n)<<endl;
    return 0;
}
点击查看AC代码

1022:整型与布尔型的转换

#include<iostream>
using namespace std;
int main(){
    int n;
    bool bl;
    cin>>n;
    bl=bool(n);
    n=bl;
    cout<<n<<endl;
    return 0;
}
点击查看AC代码

1023:Hello,World!的大小

#include<iostream>
using namespace std;
int main(){
    cout<<sizeof("Hello, World!");
    return 0;
}
点击查看AC代码

第四节 数据输入输出

1024:保留3位小数的浮点数

#include<iostream>
#include<iomanip>
using namespace std;
int main(){
    float a;
    cin>>a;
    cout<<fixed<<setprecision(3)<<a<<endl; 
    return 0;
}
点击查看AC代码

1025:保留12位小数的浮点数

#include<iostream>
#include<iomanip>
using namespace std;
int main(){
    double a;
    cin>>a;
    cout<<fixed<<setprecision(12)<<a<<endl; 
    return 0;
}
点击查看AC代码

1026:空格分隔输出

#include<iostream>
#include<iomanip>
using namespace std;
int main(){
    char a;
    int b;
    float c;
    double d;
    cin>>a>>b>>c>>d;
    cout<<a<<' '<<b<<' '<<fixed<<setprecision(6)<<c<<' '<<d<<endl; 
    return 0;
}
点击查看AC代码

1027:输出浮点数

#include<cstdio>
using namespace std;
int main(){
    double a;
    scanf("%lf",&a);
    printf("%lf\n%.5lf\n%e\n%g",a,a,a,a);
    return 0;
}
点击查看AC代码

1028:字符菱形

#include<iostream>
using namespace std;
int main(){
    int flag=0,m=3;
    char ch;
    cin>>ch;
    for(int i=1;i<=2*m-1;i++)
    {
        int tmpi=i>m?2*m-i:i;
        for(int j=1;j<m+1-tmpi;j++)
            cout<<' ';
        for(int j=1;j<=2*tmpi-1;j++)
            cout<<ch;
        cout<<'\n';
    }
        
    return 0;
}
点击查看AC代码

第五节 顺序结构实例

1029:计算浮点数相除的余

#include<iostream>
using namespace std;
#include<cmath>
int main()
{
    double    a,b;
    cin>>a>>b;
    int k=floor(a/b);
    cout<<a-k*b; 
    return 0;
}
点击查看AC代码

1030:计算球的体积

#include<iostream>
#include<iomanip>
using namespace std;
const double pi=3.14;
int main(){
    double r;
    cin>>r;
    cout<<fixed<<setprecision(2)<<4*pi/3*r*r*r<<endl;
    return 0;
}
点击查看AC代码

1031:反向输出一个三位数

#include<iostream>
using namespace std;
int main(){
    int a;
    cin>>a;
    do
    {
        cout<<a%10;
        a/=10;
    }while(a);
    return 0;
}
点击查看AC代码

1032:大象喝水查

#include<iostream>
using namespace std;
const double pi=3.14159;
int main(){
    int h,r;
    cin>>h>>r;
    cout<<int(20000/(pi*r*r*h))+1;
    return 0;
}
点击查看AC代码

1033:计算线段长度

#include<iostream>
#include<cmath>
#include<iomanip>
using namespace std;
int main(){
    double xa,ya,xb,yb;
    cin>>xa>>ya>>xb>>yb;
    cout<< fixed<<setprecision(3)<<sqrt((xa-xb)*(xa-xb)+(ya-yb)*(ya-yb));
    return 0;
}
点击查看AC代码

1034:计算三角形面积

#include<iostream>
#include<cmath>
#include<iomanip>
using namespace std;
double jl(double x1,double y1,double x2,double y2)
{
    return sqrt((x1-x2)*(x1-x2)+(y2-y1)*(y2-y1));
}
int main(){
    double x1,y1,x2,y2,x3,y3,p,a,b,c,s; 
    cin>>x1>>y1>>x2>>y2>>x3>>y3;
    a=jl(x1,y1,x2,y2);
    b=jl(x2,y2,x3,y3);
    c=jl(x1,y1,x3,y3);
    p=(a+b+c)/2;
    s=sqrt(p*(p-a)*(p-b)*(p-c));
    cout<<fixed<<setprecision(2)<<s<<endl;
    return 0;
}
点击查看AC代码

1035:等差数列末项计算

#include<iostream>
using namespace std;
int main(){
    int a1,a2,n;
    cin>>a1>>a2>>n;
    cout<<a1+(n-1)*(a2-a1);
    return 0;
}
点击查看AC代码

1036:A×B问题

#include<iostream>
using namespace std;
#include<cmath>
int main()
{
    int a,b;
    cin>>a>>b;
    cout<<1ll*a*b;
     return 0;
}
点击查看AC代码

1037:计算2的幂

#include<iostream>
using namespace std;
int main(){
    int n;
    cin>>n;
    long long m=1;
    for(int i=1;i<=n;i++)m*=2;
    cout<<m<<endl;
    return 0;
}
点击查看AC代码

1038:苹果和虫子

#include<iostream>
using namespace std;
int main(){
    int n,x,y,m;
    cin>>n>>x>>y;
    m=n-1.0*y/x;
    if(m<0)m=0;
    cout<<m<<endl;
    return 0;
}
点击查看AC代码

第三章 程序的控制结构

第一节 if选择结构

1039:判断数正负

#include<iostream>
using namespace std;
int main(){
    int n;
    cin>>n;
    if(n>0)cout<<"positive";
    else cout<<(n==0?"zero":"negative")<<endl;
    return 0;
}
点击查看AC代码

1040:输出绝对值

#include<iostream>
#include<iomanip>
using namespace std;
int main(){
    double a;
    cin>>a;
    cout<<fixed<<setprecision(2)<<(a>0?a:a*(-1));
    return 0;
}
点击查看AC代码

1041:奇偶数判断

#include<iostream>
using namespace std;
int main(){
    long a;
    cin>>a;
    cout<<(a%2?"odd":"even");
    return 0;
}
 
点击查看AC代码

1042:奇偶ASCII值判断

#include<cstdio>
int main()
{
    if(getchar()%2)printf("YES");
    else printf("NO"); 
    return 0;
}
点击查看AC代码

1043:整数大小比较

#include<iostream>
using namespace std;
int main(){
    long long a,b;
    cin>>a>>b;
    if(a>b)cout<<'>';
    else cout<<(a==b?'=':'<');
    return 0;
}
点击查看AC代码

1044:判断是否为两位数

#include<iostream>
using namespace std;
int main(){
    short n;
    cin>>n;
    if(n>=10&&n<=99)cout<<1;
    else cout<<0;
    return 0;
}
点击查看AC代码

1045:收集瓶盖赢大奖

#include<iostream>
using namespace std;
int main(){
    double a,b;
    cin>>a>>b;
    if(a>=10||b>=20)cout<<1;
    else cout<<0;
    return 0;
}
点击查看AC代码

1046:判断一个数能否同时被3和5整除

#include<iostream>
using namespace std;
int main(){
    long long n;
    cin>>n;
    if(n%3==0&&n%5==0)cout<<"YES";
    else cout<<"NO"; 
    return 0;
}
点击查看AC代码

1047:判断能否被3,5,7整除

#include<iostream>
using namespace std;
int main(){
    long long n;
    cin>>n;
    if(n%3==0&&n%5==0)cout<<"YES";
    else cout<<"NO"; 
    return 0;
}
点击查看AC代码

1048:有一门课不及格的学生

#include<iostream>
using namespace std;
int main(){
    long long n;
    cin>>n;
    if(n%3==0&&n%5==0)cout<<"YES";
    else cout<<"NO"; 
    return 0;
}
点击查看AC代码

第二节 switch语句

1049:晶晶赴约会

#include<iostream>
using namespace std;

int main()
{
    int n;
    cin>>n;
    if(n==1||n==3||n==5)cout<<"NO";
    else cout<<"YES"; 
    return 0;
}
点击查看AC代码

1050:骑车与走路

#include<iostream>
using namespace std;
int main(){
    double x,b,w;
    cin>>x;
    b=27+23+x/3;
    w=x/1.2;
    if(w>b)cout<<"Bike";
    else cout<<(w==b?"All":"Walk");
    return 0;
}
点击查看AC代码

1051:分段函数

#include<iostream>
#include<iomanip>
using namespace std;
int main(){
    float x,y;
    cin>>x;
    if(x<5)y=2.5-x;
    else if(x>=10)y=x/2-1.5;
    else y=2-1.5*(x-3)*(x-3);
    cout<<fixed<<setprecision(3)<<y;
    return 0;
}
点击查看AC代码

1052:计算邮资

#include<iostream>
using namespace std;
int main(){
    int n,p;
    char a;
    cin>>n>>a;
    p=n>1000?(8+(n-1000+499)/500*4):8;
    p+=(a=='y'?5:0);
    cout<<p;
    return 0;
}
点击查看AC代码

1053:最大数输出

#include<iostream>
using namespace std;
int main(){
    int a,b,c,maxn;
    cin>>a>>b>>c;
    maxn=a;
    if(maxn<b)maxn=b;
    if(maxn<c)maxn=c;
    cout<<maxn; 
    return 0;
}
点击查看AC代码

1054:三角形判断

#include<iostream>
using namespace std;
int main(){
    int a,b,c;
    cin>>a>>b>>c;
    if(a+b>c&&a+c>b&&b+c>a)cout<<"yes";
    else cout<<"no";
    return 0;
}
点击查看AC代码

1055:判断闰年

#include<iostream>
using namespace std;
int main(){
    int n;
    cin>>n;
    cout<<(n%100==0&&n%400!=0||n%4!=0?'N':'Y');
    return 0;
}
点击查看AC代码

1056:点和正方形的关系

#include<iostream>
using namespace std;

int main(){
    long long x,y;
    cin>>x>>y;
    if((-1<=x)&&(x<=1)&&(-1<=y)&&(y<=1))cout<<"yes";
    else cout<<"no";
    return 0;
}
点击查看AC代码

1057:简单计算器

#include<iostream>
using namespace std;

int main(){
    int a,b;
    char c;
    cin>>a>>b>>c;
    switch(c)
    {
        case '+':cout<<a+b;break;
        case '-':cout<<a-b;break;
        case '*':cout<<a*b;break;
        case '/':
            if(b==0)cout<<"Divided by zero!";
            else cout<<a/b;break;
        default:cout<<"Invalid operator!";
    }
    return 0;
} 
点击查看AC代码

1058:求一元二次方程

#include<iostream>
#include<cmath>
#include<iomanip>
using namespace std;

int main()
{
    double a,b,c;
    cin>>a>>b>>c;
    double det;
    det=b*b-4*a*c;
    if(det<-1e-12)
    {
        cout<<"No answer!";
     } 
     else
     {
         if(fabs(det)<1e-12)
         {
             cout<<"x1=x2="<<fixed<<setprecision(5)<<-b/(2*a);    
         }
         else
         {
             double x1,x2;
             x1=(-b+sqrt(det))/2/a;
             x2=(-b-sqrt(det))/2/a;
             if(x1<x2)
             {
                 cout<<"x1="<<fixed<<setprecision(5)<<x1<<";x2="<<fixed<<setprecision(5)<<x2;
             }
             else
             {
                 cout<<"x1="<<fixed<<setprecision(5)<<x2<<";x2="<<fixed<<setprecision(5)<<x1;
             }
         }
     }
    return 0;
}
点击查看AC代码

第四章 循环结构的程序设计

第一节 for语句

1059:求平均年龄

#include<iostream>
#include<iomanip>
using namespace std;

int main(){
    int n,b[1000],sum=0;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>b[i];
        sum+=b[i];
    }
    cout<<fixed<<setprecision(2)<<1.0*sum/n; 
    return 0;
}
点击查看AC代码

1060:均值

#include<iostream>
#include<iomanip>
using namespace std;

int main(){
    int n;
    cin>>n;
    double a[1000],sum=0;
    for(int i=1;i<=n;i++)
    {
        cin>>a[i];
        sum+=a[i];
    }
    cout<<fixed<<setprecision(4)<<sum/n;
    return 0;
}
点击查看AC代码

1061:求整数的和与均值

#include<iostream>
#include<iomanip>
using namespace std;

int main(){
    int n,a[10001],sum=0;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>a[i];
        sum+=a[i];
    }
    cout<<sum<<' '<<fixed<<setprecision(5)<<1.0*sum/n; 
    return 0;
}
点击查看AC代码

1062:最高的分数

#include<iostream>
using namespace std;

int main(){
    int n,a[1000],maxn=-1;
    cin>>n;
    for(int i=1;i<=n;i++){
        cin>>a[i];
        if(a[i]>maxn)maxn=a[i];
    }
    cout<<maxn;
    return 0;
}
点击查看AC代码

1063:最大跨度值

#include<iostream>
using namespace std;

int main(){
    int n,a[1001],maxn=-1,minn=1001;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>a[i];
        if(minn>a[i])minn=a[i];
        if(maxn<a[i])maxn=a[i];
     } 
     cout<<maxn-minn;
    return 0;
}
点击查看AC代码

1064:奥运奖牌计数

#include<iostream>
using namespace std;

int main(){
    int n,a,b,c,suma=0,sumb=0,sumc=0,sum;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>a>>b>>c;
        suma+=a,sumb+=b,sumc+=c; 
    }
    sum=suma+sumb+sumc;
    cout<<suma<<' '<<sumb<<' '<<sumc<<' '<<sum; 
    return 0;
}
点击查看AC代码

1065:奇数求和

#include<iostream>
using namespace std;

int main(){
    int m,n,sum=0;
    cin>>m>>n;
    for(int i=m;i<=n;i++)
        if(i%2)sum+=i;
    cout<<sum;
    return 0;
}
点击查看AC代码

1066:满足条件的数累加

#include<iostream>
using namespace std;

int main(){
    int m,n,sum=0;
    cin>>m>>n;
    for(int i=m;i<=n;i++)
        if(!(i%17))sum+=i;
    cout<<sum;
    return 0;
}
点击查看AC代码

1067:整数的个数

#include<iostream>
using namespace std;

int main(){
    int n,m,sum1=0,sum5=0,sum10=0;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>m;
        if(m==1)sum1++;
        if(m==5)sum5++;
        if(m==10)sum10++;
    }
    cout<<sum1<<'\n'<<sum5<<'\n'<<sum10;
    return 0;
}
点击查看AC代码

1068:与指定数字相同的数的个数

#include<iostream>
using namespace std;

int main(){
    int n,x,m,sum=0;
    cin>>n>>m;
    for(int i=1;i<=n;i++)
    {
        cin>>x;
        if(x==m)sum++;
    }
    cout<<sum;
    return 0;
}
点击查看AC代码

1069:乘方计算

#include<iostream>
using namespace std;

int main(){
    int a,n,ans=1;
    cin>>a>>n;
    for(int i=1;i<=n;i++)
        ans*=a;
    cout<<ans;
    return 0;
}
点击查看AC代码

1070:人口增长

#include<iostream>
#include<iomanip>
using namespace std;

int main(){
    double a,n,ans=1;
    cin>>a>>n;
    for(int i=1;i<=n;i++)
        ans*=1.001;
    cout<<fixed<<setprecision(4)<<ans*a;
    return 0;
}
点击查看AC代码

1071:菲波那契数

#include<iostream>
using namespace std;

int main(){
    int k,a[50];
    cin>>k;
    a[1]=1,a[2]=1;
    for(int i=3;i<=k;i++) 
        a[i]=a[i-1]+a[i-2];
    cout<<a[k];
    return 0;
}
点击查看AC代码

1072:鸡尾酒疗法

#include<iostream>
#include<cmath>
#include<cstdio>
using namespace std;
int main()
{
    int n;
    double z,y,z1,y1,jd=1e-6;
    double new1,old;
    cin>>n;
    cin>>z>>y;
    old=y/z; //这个计算要放在循环外面才行 
    for(int i=0;i<n-1;i++)
    {
        cin>>z1>>y1;
        new1=y1/z1;
        old=y/z; //这个计算要放在循环外面才行 
        if(new1-old>0.05-jd) cout<<"better"<<endl;
        else if((old-new1)>0.05-jd) cout<<"worse"<<endl;
        else cout<<"same"<<endl;
    }
    return 0;
}
点击查看AC代码

1073:救援

#include<iostream>
#include<cmath>
using namespace std;

int main(){
    double n,a,b,c,sum=0;
    int s;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>a>>b>>c;
        sum+=sqrt(a*a+b*b)/25+1.5*c; 
    }
    s=ceil(sum);
    cout<<s;
    return 0;
}
点击查看AC代码

1074:津津的储蓄计划

#include<iostream>
using namespace std;

int main(){
    int a[13],b=0,sum=0,i;
    for(i=1;i<=12;i++)cin>>a[i];
    for(i=1;i<=12;i++)
    {        
        b+=300-a[i];
        if(b<0)break;
        sum+=b/100*100;
        b%=100;
    }
    if(i==13)cout<<1.2*sum+b;
    else cout<<-i;
    return 0;
}
点击查看AC代码

1075:药房管理

#include<iostream>
using namespace std;

int main(){
    int n,m,a,ans=0;
    cin>>n>>m;
    for(int i=1;i<=m;i++)
    {
        cin>>a;
        if(n>=a)n-=a;
        else ans++;
    }
    cout<<ans;
    return 0;
}
点击查看AC代码

1076:正常血压

#include<iostream>
using namespace std;

int main(){
    int n,a,b,ans=0,maxn=-1;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>a>>b;
        if(90<=a&&a<=140&&60<=b&&b<=90){
            ans++;
            if(ans>maxn)maxn=ans;
        }
        else ans=0;
    }
    cout<<maxn;
    return 0;
}
点击查看AC代码

1077:统计满足条件的4位数

#include<iostream>
using namespace std;

int main(){
    int n,a,a1,a2,a3,a4,ans=0;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>a;
        a1=a%10;
        a2=a/10%10;
        a3=a/100%10;
        a4=a/1000;
        if(a1>a2+a3+a4)ans++;
    }
    cout<<ans;
    return 0;
}
点击查看AC代码

1078:求分数序列和

#include<iostream>
#include<iomanip>
using namespace std;

int main(){
    float n,p,q,tmp,ans=0;
    p=1,q=2,ans=q/p;
    cin>>n;
    for(int i=2;i<=n;i++)
    {        
        tmp=q;
        q+=p;
        p=tmp;
        ans+=q/p;
    }
    cout<<fixed<<setprecision(4)<<ans;
    return 0;
}
点击查看AC代码

1079:计算分数加减表达式的值

#include<iostream>
#include<iomanip>
using namespace std;

int main(){
    int n;
    double s;
    cin>>n;
    for(int i=1;i<=n;i++)
    s+=(i%2?1.0/i:-1.0/i);
    cout<<fixed<<setprecision(4)<<s; 
    return 0;
}
点击查看AC代码

1080:余数相同问题

#include<iostream>
using namespace std;

int main(){
    int a,b,c,ans;
    cin>>a>>b>>c;
    for(int i=2;i<=a||a<=b||a<=c;i++)
        if(a%i==b%i&&a%i==c%i)
        {
            ans=i;
            break;
        }
    cout<<ans;
    return 0;
}
点击查看AC代码

1081:分苹果

#include<iostream>
using namespace std;

int main(){
    int n;
    cin>>n;
    cout<<n*(n+1)/2; 
    return 0;
}
点击查看AC代码

1082:求小数的某一位

#include<iostream>
using namespace std;

int main(){
    int a,b,c,ans;
    cin>>a>>b>>c;
    a%=b;
    for(int i=1;i<=c;i++)
    { 
        ans=a*10/b;
        a=a*10%b;
    }
    cout<<ans;
    return 0;
}
点击查看AC代码

1083:计算星期几

#include<iostream>
#include<cmath>
#include<cstdio>
using namespace std;
int main()
{
    int a,b,xh=0,sum=1;//循环
    int yx;//有效的次方 
    cin>>a>>b;
    a%=7;
    for(int i=1;i<=b;i++)
    {
        sum=sum*a;
        if((sum%7==a)&&i>1)
        {
            xh=i-1;
            break;
        }
    }
    if(xh>1)
    {
        yx=int(pow(a,b%xh))%7;
    }
    else
    {
        yx=sum%7;

    }
    switch(yx)
    {
        case 1:cout<<"Monday";break;
        case 2:cout<<"Tuesday";break;
        case 3:cout<<"Wednesday";break;
        case 4:cout<<"Thursday";break;
        case 5:cout<<"Friday";break;
        case 6:cout<<"Saturday";break;
        case 0:cout<<"Sunday";break;
    }
    
    return 0;
}
点击查看AC代码1084幂的末尾
#include<iostream>
#include<iomanip>
using namespace std;

int main(){
    int a,b,ans;
    cin>>a>>b;
    ans=a%1000;
    for(int i=1;i<b;i++)
    ans=ans*a%1000; 
    cout<<setfill('0')<<setw(3)<<ans;    
    return 0;
}
点击查看AC代码

第二节 while语句

1085:球弹跳高度的计算

#include<iostream>
using namespace std;

int main(){
    double h0,n=10,s,h;
    cin>>h0;
    s=-h0,h=h0;
    for(int i=1;i<=n;i++)
    {
        s+=h*2;
        h/=2; 
     } 
     cout<<s<<'\n'<<h;
    return 0;
}
点击查看AC代码

1086:角谷猜想

#include<iostream>
using namespace std;

int main(){
    int n;
    cin>>n;
    while(n!=1){
        if(n%2){
            cout<<n<<"*3+1=";
            n=n*3+1;
            cout<<n<<'\n';
        }
        else
        {
            cout<<n<<'/'<<2<<'=';
            n/=2;
            cout<<n<<'\n';
            
        }
    }
    cout<<"End";
    return 0;
}
点击查看AC代码

1087:级数求和

#include<iostream>
using namespace std;

int main(){
    double k,ans=0;
    long long n=1;
    cin>>k;
    while(ans<=k+(1e-16))
    {
        ans+=1.0/n++;
    }
    cout<<n-1;
    return 0;
}
点击查看AC代码

1088:分离整数的各个数

#include<iostream>
using namespace std;

int main(){
    int n;
    cin>>n;
    cout<<n%10;
    n/=10;
    while(n)
    {
        cout<<' '<<n%10;
        n/=10;
    }
    return 0;
}
点击查看AC代码

1089:数字反转

#include<iostream>
using namespace std;

int main(){//余数自带符号,如(-31)%10=-1 
    int n,ans=0;
    cin>>n;
    while(n)
    {
        ans=ans*10+n%10;
        n/=10;
    }
    cout<<ans;
    return 0;
}
点击查看AC代码

1090:含k个3的数

#include<iostream>
using namespace std;

int main(){
    int n,k,ans=0;
    cin>>n>>k;
    if(n%19)
        cout<<"NO";
    else
    {
        while(n)
        {
            if(n%10==3)ans++;
            n/=10;
        }
        if(ans==k)cout<<"YES";
        else cout<<"NO";
    }        
    return 0;
}
点击查看AC代码

第三节 do-while语句

1085:球弹跳高度的计算

//1085:球弹跳高度的计算
#include<iostream>
using namespace std;
int main(){
    double h,ans,i;
    cin>>h;
    ans=-h;
    i=0;
    do
    {        
        ans+=h*2;
        h/=2;
        i++;
    }while(i<10);
    cout<<ans<<endl<<h;
    return 0;
}
点击查看AC代码

1086:角谷猜想

//1086:角谷猜想
#include<iostream>
using namespace std;
int main(){
    int n;
    cin>>n;
    do
    {
        cout<<n;
        if(n%2)
        {
            cout<<"*3+1=";
            n=n*3+1;
        }
        else
        {
            cout<<"/2=";
            n/=2;
        }
        cout<<n<<endl;
    }while(n!=1);
    cout<<"End"<<endl;
    return 0;
}
点击查看AC代码

1087:级数求和

//1087:级数求和
#include<iostream>
using namespace std;
int main(){
    double s=0;
    int k,n=0;
    cin>>k;
    do
    {
        n++;
        s+=1.0/n;
    }while(s-k<1e-12);
    cout<<n;
    return 0;
}
点击查看AC代码

1088:分离整数的各个数

//1088:分离整数的各个数
#include<iostream>
using namespace std;
int main(){
    int n;
    cin>>n;
    do
    {
        cout<<n%10<<' ';
        n/=10;
    }while(n);
    return 0;
}
点击查看AC代码

1089:数字反转

//1089:数字反转
#include<iostream>
using namespace std;
int main(){
    int n,ans=0,f=1;
    cin>>n;
    if(n<0)f=-1,n=-n;
    do
    {
        ans=ans*10+n%10;
        n/=10;
    }while(n);
    ans*=f;
    cout<<ans;
    return 0;
}
点击查看AC代码

1090:含k个3的数

//1090:含k个3的数
#include<iostream>
using namespace std;
int main(){
    int n,k;
    cin>>n>>k;
    do
    {
        if(n%10==3)k--;
        n/=10;
    }while(n);
    if(k)cout<<"NO";
    else cout<<"YES";
    return 0;
}
点击查看AC代码

第四节 循环嵌套

1091:求阶乘的和

#include<iostream>
using namespace std;
long long a[100];
int main(){
    int n;
    long long sum=0;
    cin>>n;
    a[0]=1;
    for(int i=1;i<=n;i++)
    {
        a[i]=a[i-1]*i ;
        sum+=a[i];
    }
    cout<<sum;
    return 0;
}
点击查看AC代码

1092:求出e的值

#include<iostream>
#include<iomanip>
using namespace std;
double a[1000];
int main(){
    double n, sum=1;
    cin>>n;
    a[0]=1;
    for(int i=1;i<=n;i++)
    {
        a[i]=a[i-1]/i ;
        sum+=a[i];
    }
    cout<<fixed<<setprecision(10)<<sum;
    return 0;
}
点击查看AC代码

1093:计算多项式的值

#include<iostream>
#include<cmath>
#include<iomanip>
using namespace std;
int main()
{
    double x,b;
    int n;
    cin>>x>>n;
    b=(pow(x,n+1)-1)/(x-1);
     cout<<fixed<<setprecision(2)<<b;
    return 0;
}
点击查看AC代码

1094:与7无关的数

#include<iostream>
using namespace std;
bool cont(int n)
{
    while(n)
    {
        if(n%10==7)return true;
        n/=10;
    }
    return false;
}
int main(){
    int n,sum=0;
    cin>>n;
    for(int i=1;i<=n;i++)
        if(!cont(i)&&(i%7))sum+=i*i;
    cout<<sum;
    return 0;
}
点击查看AC代码

1095:数1的个数

#include<iostream>
using namespace std;
int num1(int n)
{
    int sum=0;
    while(n)
    {
        if(n%10==1)sum++;
        n/=10;
    }
    return sum;
}
int main(){
    int n,ans=0;
    cin>>n;
    for(int i=1;i<=n;i++)
        ans+=num1(i);
    cout<<ans;
    return 0;
}
点击查看AC代码

1096:数字统计

#include<iostream>
using namespace std;
int num2(int n)
{
    int sum=0;
    while(n)
    {
        if(n%10==2)sum++;
        n/=10;
    }
    return sum;
}
int main(){
    int n,m,ans=0;
    cin>>n>>m;
    for(int i=n;i<=m;i++)
        ans+=num2(i);
    cout<<ans;
    return 0;
}
点击查看AC代码

1097:画矩形

#include<iostream>
using namespace std;
void jx(int a,int b,char c,int d)
{
    char e=(d==1?c:' '),f;
    for(int i=1;i<=a;i++)
    {    
        for(int j=1;j<=b;j++)
        {
            if(i==1||i==a||j==1||j==b)f=c;
            else f=e;
            cout<<f;
        }
        cout<<endl;
    }
}
int main(){
    int n,m,a;
    char b;
    cin>>n>>m>>b>>a;
    jx(n,m,b,a);
    return 0;
}
点击查看AC代码

1098:质因数分解

#include<iostream>
using namespace std;
int main()
{
    int n;
    cin>>n;
    for(int i=2;i<=n/i;i++)
        if(n%i==0)
            cout<<n/i; 
    return 0;
}
点击查看AC代码

1099:第n小的质数

#include<iostream>
using namespace std;
int a[10001],k=1;
bool prime(int n)
{
    for(int i=1;i<=k;i++)
        if(n%a[i]==0)return false;
    return true;
 } 
int main(){
    int n;
    cin>>n;
    a[1]=2;
    for(int i=3;k<=n;i+=2)
        if(prime(i))a[++k]=i;
    cout<<a[n];
    return 0;
}
点击查看AC代码

1100:金币

#include<iostream>
using namespace std;
int main(){
    int n,i=0,sum=0,ans=0;
    cin>>n;
    while(sum<=n)sum+=++i;
    i--;
    sum-=i+1;
    for(int j=1;j<=i;j++)
        ans+=j*j;
    ans+=(i+1)*(n-sum);
    cout<<ans;
    return 0;
}
点击查看AC代码

1101:不定方程求解

#include<iostream>
using namespace std;

int main(){
    int a,b,c,ans=0;
    cin>>a>>b>>c;
    for(int i=0;i<=c/a;i++)
        if((c-a*i)%b==0)ans++;
    cout<<ans;
    return 0;
}
点击查看AC代码

第五章 数 组

第一节 一维数组

1102:与指定数字相同的数的个数

#include<iostream>
using namespace std;

int main(){
    int n,b,c[101],ans=0;
    cin>>n;
    for(int i=1;i<=n;i++)cin>>c[i];
    cin>>b;
    for(int i=1;i<=n;i++)
        if(c[i]==b)ans++;
    cout<<ans;
    return 0;
}
点击查看AC代码

1103:陶陶摘苹果

#include<iostream>
using namespace std;

int main(){
    int a[11],h,ans=0;
    for(int i=1;i<=10;i++)cin>>a[i];
    cin>>h;
    for(int i=1;i<=10;i++)
        if(a[i]<=h+30)ans++;
    cout<<ans;
    return 0;
}
点击查看AC代码

1104:计算书费

#include<iostream>
#include<iomanip>
using namespace std;

int main(){
    float a[11]={0,28.9,32.7,45.6,78,35,86.2,27.8,43,56,65},sum=0;
    int n;
    for(int i=1;i<=10;i++)
    {
        cin>>n;
        sum+=a[i]*n;
    }
    cout<<fixed<<setprecision(1)<<sum;
    return 0;
}
点击查看AC代码

1105:数组逆序重存放

#include<iostream>
using namespace std;

int main(){
    int n,a[101];
    cin>>n;
    for(int i=n;i>0;i--)cin>>a[i];
    for(int i=1;i<=n;i++)cout<<a[i]<<' ';
    
    return 0;
}
点击查看AC代码

1106:年龄与疾病

#include<iostream>
#include<iomanip>
using namespace std;
int n,b[5],a;
int main(){
    
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>a;
        if(a<=18)b[1]++;
        else if(a<=35)b[2]++;
        else if(a<=60)b[3]++;
        else b[4]++; 
    }
    for(int i=1;i<=4;i++)cout<<fixed<<setprecision(2)<<1.0*b[i]/n*100<<'%'<<'\n';
    return 0;
}
点击查看AC代码

1107:校门外的树

#include<iostream>
using namespace std;
int a[10001];
int main(){
    int l,n,c,b,ans=0;
    cin>>l>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>c>>b;
        for(int j=c;j<=b;j++)
            a[j]=1;
    }
    for(int i=0;i<=l;i++)
        if(a[i]==0)ans++;
    cout<<ans;
    return 0;
}
点击查看AC代码

1108:向量点积计算

#include<iostream>
using namespace std;

int main(){
    int n,a[1001],b,sum=0;
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i];
    for(int i=1;i<=n;i++)
    {
        cin>>b;
        sum+=a[i]*b;
    }
    cout<<sum;
    return 0;
}
点击查看AC代码

1109:开关灯

#include<iostream>
using namespace std;
bool d[5001]; 
int main(){
    int n,m;
    cin>>n>>m;
    for(int i=1;i<=m;i++)
        for(int j=i;j<=n;j++)
            if(j%i==0)d[j]=!d[j];
    cout<<1;
    for(int i=2;i<=n;i++)
        if(d[i])cout<<','<<i;
    return 0;
}
点击查看AC代码

1110:查找特定的值

#include<iostream>
using namespace std;
int n,a[10001],m,i;
int main(){
    
    cin>>n;
    for(i=1;i<=n;i++)cin>>a[i];
    cin>>m;
    i=1;
    while(a[i]!=m&&i<=n)i++;
    if(i==n+1)cout<<-1;
    else cout<<i;
    return 0;
}
点击查看AC代码

1111:不高兴的津津

#include<iostream>
using namespace std;

int main(){
    int n,m,i,s,maxn=0,max=8;
    for(i=1;i<=7;i++)
    {
        cin>>n>>m;
        if(n+m>max)max=n+m,maxn=i;
    }
    cout<<maxn;
    return 0;
}
点击查看AC代码

1112:最大值和最小值的差

#include<iostream>
using namespace std;

int main(){
    int n,m,max=-10001,min=10001;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>m;
        if(m>max)max=m;
        if(m<min)min=m;
    }
    cout<<max-min;
    return 0;
}
点击查看AC代码

1113:不与最大数相同的数字之和

#include<iostream>
using namespace std;

int main(){
    int n,m,max=-1000001,k,ans=0;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>m;
        ans+=m;
        if(m>max)
        {
            k=1;
            max=m;
        }
        else if(m==max)k++;
    }
    ans-=max*k;
    cout<<ans;
    return 0;
}
点击查看AC代码

1114:白细胞计数

#include<iostream>
#include<iomanip>
using namespace std;
double a[301],m,max1=-1,max2,min1=(1<<31)-1,min2,sum=0,aver,jd;
int main(){
    int n;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>m;
        sum+=m;
        if(m>max1){
            max2=max1;
            max1=m;
        }
        else if(m>max2)max2=m;
        if(m<min1){
            min2=min1;
            min1=m;
        }
        else if(m<min2)min2=m;
     } 
     aver=(sum-max1-min1)/(n-2);
     jd=max2-aver>aver-min2?max2-aver:aver-min2;
     cout<<fixed<<setprecision(2)<<aver<<' '<<jd;
    return 0;
}
点击查看AC代码

1115:直方图

#include<iostream>
using namespace std;
int a[10002];
int main(){
    int n,m,max=-1;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>m;
        if(max<m)max=m;
        a[m]++;
    }
    for(int i=0;i<=max;i++)
    cout<<a[i]<<endl;
    return 0;
}
点击查看AC代码

1116:最长平台

#include<iostream>
using namespace std;

int main(){
    int n;
    int m,fr=-1,ln=1,mn=0;
    cin>>n;
    cin>>fr;
    for(int i=1;i<n;i++)
    {
        cin>>m;
        if(m==fr){
            ln++;
            if(mn<ln)mn=ln;
        }
        else ln=1,fr=m;
    }
    cout<<mn;
    return 0;
}
点击查看AC代码

1117:整数去重

#include<iostream>
using namespace std;
int a[20001],b[20001];
int main(){
    int n,m,k=0,f=0;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>m;
        if(!a[m])a[m]=1,b[++f]=m;
    }
    for(int i=1;i<=f;i++)
        if(k==0)
        {
            cout<<b[i];
            k=1;
        }
        else cout<<' '<<b[i];
    return 0;
}
点击查看AC代码

1118:铺地毯

#include<iostream>
using namespace std;
int a[10000][4];
int main(){
    int n,x,y,ans=0;
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i][0]>>a[i][1]>>a[i][2]>>a[i][3];
    cin>>x>>y;
    for(int i=n;i>=1;i--)
    {
        if(a[i][0]<=x&&x<=a[i][0]+a[i][2]&&a[i][1]<=y&&y<=a[i][1]+a[i][3])
            {
                cout<<i;
                ans=1;
                break;
            }
    }
    if(ans==0)cout<<-1;
    return 0;
}
点击查看AC代码

第二节 二维数组

1119:矩阵交换行

#include<iostream>
using namespace std;
int a[6][6];
int main(){
    int n,m;
    for(int i=1;i<=5;i++)
        for(int j=1;j<=5;j++)cin>>a[i][j];
    cin>>n>>m;
    for(int i=1;i<=5;i++)swap(a[n][i],a[m][i]);
    for(int i=1;i<=5;i++)
    {
        for(int j=1;j<5;j++)
            cout<<a[i][j]<<' ';
        cout<<a[i][5]<<'\n';
    }
        
    return 0;
}
点击查看AC代码

1120:同行列对角线的格

#include<iostream>
using namespace std;
void pt(int x,int y,int z)
{
    if(z==-1)cout<<' ';
    cout<<'('<<x<<','<<y<<')';
    if(z==1)cout<<' ';
    if(z==2)cout<<'\n';
}
int main(){
    int n,i,j,f=0;
    cin>>n>>i>>j;
    for(int k=1;k<n;k++)
        pt(i,k,1);
    pt(i,n,2);
    for(int k=1;k<n;k++)
        pt(k,j,1);
    pt(n,j,2);
    for(int k=1;k<=n;k++)
        if(i-j+1<=k&&k<=n+i-j)
            if(f==0)
            {
                pt(k,k-i+j,0);
                f=1;
            }
            else pt(k,k-i+j,-1);
    cout<<'\n';
    f=0;
    for(int k=n;k>0;k--)
        if(i+j-n<=k&&k<=i+j-1)
            if(f==0)
            {
                pt(k,i+j-k,0);
                f=1;
            }
            else pt(k,i+j-k,-1);
    return 0;
}
点击查看AC代码-1
//1120:同行列对角线的格 
#include<cstdio>
int main(){
    int n,x,y;
    scanf("%d %d %d",&n,&x,&y);
    for(int i=1;i<=n;i++)printf("(%d,%d) ",x,i);
    printf("\n");
    for(int i=1;i<=n;i++)printf("(%d,%d) ",i,y);
    printf("\n");
    for(int i=1;i<=n;i++)
        if(y-x+i>0&&y-x+i<=n)printf("(%d,%d) ",i,y-x+i);
    printf("\n");
    for(int j=1;j<=n;j++)
        if(x+y-j>0&&x+y-j<=n)printf("(%d,%d) ",x+y-j,j);
    return 0;
}
点击查看AC代码-2

1121:计算矩阵边缘元素之和

#include<iostream>
using namespace std;

int main(){
    int m,n,sum=0,a[101][101];
    cin>>m>>n;
    for(int i=1;i<=m;i++)
        for(int j=1;j<=n;j++)cin>>a[i][j];
    for(int i=1;i<=m;i++)
        for(int j=1;j<=n;j++)
            if(i==1||i==m||j==1||j==n)sum+=a[i][j];
    cout<<sum;
    return 0;
}
点击查看AC代码

1122:计算鞍点

#include<iostream>
using namespace std;
int a[6][6],h[6],l[6];
int main(){
    int mh,mn,ml,ln,f=0;
    for(int i=1;i<=5;i++)
        for(int j=1;j<=5;j++)cin>>a[i][j]; 
    for(int i=1;i<=5;i++)
    {
        mh=-1,ml=(1<<31)-1;
        for(int j=1;j<=5;j++)
        {
            if(mh<a[i][j])mh=a[i][j],h[i]=j;
            if(ml>a[j][i])ml=a[j][i],l[i]=j;
        }
    }
    for(int i=1;i<=5;i++)
        if(l[h[i]]==i)
        {
            cout<<i<<' '<<h[i]<<' '<<a[i][h[i]]<<endl;
            f=1;
        }
    if(f==0)cout<<"not found";
    return 0;
}
点击查看AC代码

1123:图像相似度

#include<iostream>
#include<iomanip>
using namespace std;
int a[101][101],b[101][101]; 
int main(){
    int m,n,ans=0;
    cin>>m>>n;
    for(int i=1;i<=m;i++)
        for(int j=1;j<=n;j++)cin>>a[i][j];
    for(int i=1;i<=m;i++)
        for(int j=1;j<=n;j++)
    {
        cin>>b[i][j];
        if(b[i][j]==a[i][j])ans++;
    }
    cout<<fixed<<setprecision(2)<<1.0*ans/m/n*100;
    return 0;
}
点击查看AC代码

1124:矩阵加法

#include<iostream>
#include<iomanip>
using namespace std;
int a[101][101],b[101][101]; 
int main(){
    int m,n;
    cin>>m>>n;
    for(int i=1;i<=m;i++)
        for(int j=1;j<=n;j++)cin>>a[i][j];
    for(int i=1;i<=m;i++)
        for(int j=1;j<=n;j++)
    {
        cin>>b[i][j];
        a[i][j]+=b[i][j];
    }
    for(int i=1;i<=m;i++)
    {
        for(int j=1;j<=n;j++)cout<<a[i][j]<<' ';
        cout<<endl;
    }
        
    return 0;
}
点击查看AC代码

1125:矩阵乘法

#include<iostream>
#include<iomanip>
using namespace std;
int a[101][101],b[101][101],c[101][101]; 
int main(){
    int n,m,k;
    cin>>n>>m>>k;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)cin>>a[i][j];
    for(int i=1;i<=m;i++)
        for(int j=1;j<=k;j++)cin>>b[i][j];
    for(int i=1;i<=n;i++)
        for(int j=1;j<=k;j++)
            for(int l=1;l<=m;l++)
                c[i][j]+=a[i][l]*b[l][j];        
    for(int i=1;i<=n;i++)
    {
        for(int j=1;j<=k;j++)
            cout<<c[i][j]<<' ';
        cout<<endl;
    }    
    return 0;
}
点击查看AC代码

1126:矩阵转置

#include<iostream>
using namespace std;

int a[101][101],b[101][101]; 
int main(){
    int n,m;
    cin>>n>>m;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)cin>>a[i][j];
    for(int i=1;i<=m;i++)
        for(int j=1;j<=n;j++)
            b[i][j]=a[j][i];        
    for(int i=1;i<=m;i++)
    {
        for(int j=1;j<=n;j++)
            cout<<b[i][j]<<' ';
        cout<<endl;
    }    
    return 0;
}
点击查看AC代码

1127:图像旋转

#include<iostream>
using namespace std;

int a[101][101],b[101][101]; 
int main(){
    int n,m;
    cin>>n>>m;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)cin>>a[i][j];
    for(int i=1;i<=m;i++)
        for(int j=1;j<=n;j++)
            b[i][j]=a[n+1-j][i];        
    for(int i=1;i<=m;i++)
    {
        for(int j=1;j<=n;j++)
            cout<<b[i][j]<<' ';
        cout<<endl;
    }    
    return 0;
}
点击查看AC代码

1128:图像模糊处理

#include<iostream>
using namespace std;

int a[101][101],b[101][101]; 
int main(){
    int n,m;
    cin>>n>>m;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)cin>>a[i][j];
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)
        {
            if(i==1||i==n||j==1||j==m)
                b[i][j]=a[i][j];
            else
                b[i][j]=((a[i][j]+a[i-1][j]+a[i+1][j]+a[i][j-1]+a[i][j+1])/5.0+0.5);
        }        
    for(int i=1;i<=n;i++)
    {
        for(int j=1;j<m;j++)
            cout<<b[i][j]<<' ';
        cout<<b[i][m]<<endl;
    }    
    return 0;
}
点击查看AC代码

第三节 字符类型和字符数组

1129:统计数字字符个数

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;

int main(){
    char ch[10000];
    int ans=0;
    gets(ch);
    for(int i=0;i<strlen(ch);i++)
        if('0'<=ch[i]&&ch[i]<='9')ans++;
    cout<<ans;
    return 0;
}
点击查看AC代码

1130:找第一个只出现一次的字符

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
int b[26];
string ch;
int main(){
    getline(cin,ch);
    for(int i=0;i<ch.size();i++)
        b[ch[i]]++;
    for(int i=0;i<ch.size();i++)
        if(b[ch[i]]==1)
        {
            cout<<ch[i];
            return 0;
        }
    cout<<"no";
    return 0;
}
点击查看AC代码

1131:基因相关性

#include<iostream>
#include<cstring>
using namespace std;

int main(){
    double n,m;
    cin>>n;
    string s1,s2;
    cin>>s1>>s2;
    int s=s1.size(),ans=0;
    for(int i=0;i<s;i++)
        if(s1[i]==s2[i])ans++;
    m=ans*1.0/s;
    if(m-n>1e-16)cout<<"yes";
    else cout<<"no";
    return 0;
}
点击查看AC代码

1132:石头剪子布

#include<iostream>
using namespace std;
int si(string s)
{
    if(s=="Rock")return 0;
    if(s=="Scissors")return 1;
    if(s=="Paper")return 2; 
}
int main(){
    string p1,p2,re[3]={"Tie","Player2","Player1"};
    int n,a,b,ans[101]; 
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>p1>>p2;
        ans[i]=(si(p1)-si(p2)+3)%3;
    }
    for(int i=1;i<=n;i++)
        cout<<re[ans[i]]<<endl;
    return 0;
}
点击查看AC代码

1133:输出亲朋字符串

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;

int main(){
    string s1;
    char s2[101];
    cin>>s1;
    int n=s1.size();
    for(int i=0;i<n-1;i++)
        s2[i]=s1[i]+s1[i+1];
    s2[n-1]=s1[n-1]+s1[0];
    s2[n]='\0';
    cout<<s2;
    return 0;
}
点击查看AC代码

1134:合法C标识符查

#include<bits/stdc++.h>
using namespace std;
char a[21];
int main()
{
    int ans=0;
    scanf("%s",a);
    int len=strlen(a);
    for(int i=0;i<len;i++)
    {
        int ch=a[i];
        if(!(ch>='0'&&ch<='9'||ch>='A'&&ch<='Z'||ch=='_'||ch>='a'&&ch<='z'))ans=1;
    }
    if(a[0]>='0'&&a[0]<='9')ans=1;
    if(ans==0)cout<<"yes"; 
    else cout<<"no";
    return 0;
}
点击查看AC代码

1135:配对碱基链

#include<iostream>
#include<cstring>
using namespace std;
char atgc(char ch)
{
    switch(ch){    
    case 'A':return 'T';
    case 'T':return 'A';
    case 'G':return 'C';
    default:return 'G';}
}
int main(){
    char s1[256],s2[256];
    cin>>s1;
    int n=strlen(s1);
    for(int i=0;i<n;i++)
    cout<<atgc(s1[i]);
    return 0;
}
点击查看AC代码

1136:密码翻译

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
char ed(char ch)
{
    if(ch>='a'&&ch<='y')return ch+1;
    if(ch>='A'&&ch<='Y')return ch+1;
    if(ch=='z')return 'a'; 
    if(ch=='Z')return 'A'; 
    return ch;
}
int main(){
    char c[81];
    gets(c);
    int n=strlen(c);
    for(int i=0;i<n;i++)
    cout<<ed(c[i]);
    return 0;
}
点击查看AC代码

1137:加密的病历单

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
char ed(char ch)
{
    if(ch>96)ch=(ch-94)%26+65;
    else ch=(ch-62)%26+97;
    return ch;
}
int main(){
    char s[51];
    cin>>s;
    int n=strlen(s);
    for(int i=n-1;i>=0;i--)
    cout<<ed(s[i]);
    return 0;
}
点击查看AC代码

1138:将字符串中的小写字母转换成大写字母

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;

int main(){
    char ch[101];
    gets(ch);
    int n=strlen(ch);
    for(int i=0;i<n;i++)
    {
        if(ch[i]>='a'&&ch[i]<='z')ch[i]-=32;
        cout<<ch[i];
    }
    return 0;
}
点击查看AC代码

1139:整理药名

#include<iostream>
#include<cstdio>
#include<cstring> 
using namespace std;
string ed(string ch)
{
    if(ch[0]>='a'&&ch[0]<='z')ch[0]-=32;
    int n=ch.size() ;
    for(int i=1;i<n;i++)
        if(ch[i]>='A'&&ch[i]<='Z')ch[i]+=32;
    return ch;
}
int main(){
    string s[101];
    int n;
    cin>>n;
    for(int i=1;i<=n;i++)cin>>s[i];
    for(int i=1;i<=n;i++)cout<<ed(s[i])<<endl;;
    return 0;
}
点击查看AC代码

1140:验证子串

#include<iostream>
#include<cstring>

using namespace std;

int main(){
    string s1,s2;
    cin>>s1>>s2;
    int n1=s1.size() ,n2=s2.size() ,an=0;
    if(n1>n2){
        swap(s1,s2);
        swap(n1,n2);
    }
    for(int i=0;i<=n2-n1;i++)
        {
            an=0;
            while(an<n1&&s1[an]==s2[an+i])an++;
            if(an==n1)
            {
                cout<<s1<<" is substring of "<<s2;
                return 0;
            }
        }
    cout<<"No substring"; 
    return 0;
}
点击查看AC代码

1141:删除单词后缀

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;

int main()
{
    string s;
    cin>>s;
    int n=s.size() ; 
    if(s.substr(n-2,2)=="er"||s.substr(n-2,2)=="ly" )
        s=s.substr(0,n-2);
    else if(s.substr(n-3,3)=="ing" ) s=s.substr(0,n-3);
    cout<<s; 
     return 0;
}
点击查看AC代码

1142:单词的长度

#include<iostream>
using namespace std;
string s;
int main()
{
    int f=0;
    while(cin>>s)
    {
        int len=s.size();
        if(f)cout<<',';
        cout<<len;
        f=1; 
    }
    return 0;
}
点击查看AC代码

1143:最长最短单词

#include<iostream>
#include<cstring>
#include<cstdio>
#include<string>
using namespace std;

int main()
{
    string s,mx,mi;
    int h=0,max=0,min=101,m,l;
    getline(cin,s);
    //s+=" ";
    m=s.size() ;
    for(int j=0;j<=m;j++)
    {
        if(s[j]==' '||s[j]==','||s[j]=='\0')
        {
            if(h!=j)
            {
                l=j-h;
                if(l<min)
                {
                    min=l;
                    mi=s.substr(h,l); 
                } 
                if(l>max)
                {
                    max=l;
                    mx=s.substr(h,l);
                }
            }
            h=j+1;
        }
        else if(h==j)h=j;
    }
    cout<<mx<<endl<<mi;
     return 0;
}
点击查看AC代码

1144:单词翻转

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
string retu(string ss)
{
    int n=ss.size() ;
    for(int i=0;i<=(n-1)/2;i++)
    swap(ss[i],ss[n-1-i]);
    return ss;
}
int main(){
    string s,ss="",st;
    int h=0,l;
    getline(cin,s);
    for(int i=0;i<=s.size();i++)
    {
        if(s[i]==' '||s[i]=='\0')            
        {
            if(i!=h)
            {
                l=i-h;
                st=s.substr(h,l);
                ss+=retu(st);
            }
            if(s[i]=32)ss+=s[i];
            h=i+1;
        }
    }
    cout<<ss.substr(0,s.size())<<endl;
    return 0;
}
点击查看AC代码

1145:字符串p型编码

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;

int main(){
    string s;
    int l=1;
    getline(cin,s);
    for(int i=0;i<s.size() ;i++)
    {
        if(s[i]==s[i+1])l++;
        else
        {
            cout<<l<<s[i];
            l=1;
        }
    }
    return 0;
}
点击查看AC代码

1146:判断字符串是否为回文

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
bool pd(string s)
{
    int n=s.size();
    for(int i=0;i<=(n-1)/2;i++)
        if(s[i]!=s[n-1-i])return false;
    return true;
}
int main(){
    string s;
    getline(cin,s);
    if(pd(s))cout<<"yes";
    else cout<<"no";
    return 0;
}
点击查看AC代码

1147:最高分数的学生姓名

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;

int main(){
    int n;
    int cj[101],max=-1,maxn;
    string xm[101];
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>cj[i]>>xm[i]; 
        if(cj[i]>max)max=cj[i],maxn=i;
    }
     cout<<xm[maxn];
    return 0;
}
点击查看AC代码

1148:连续出现的字符

#include <bits/stdc++.h>
using namespace std;
int main()
{   char s[2502],old;
    int i,t=1,k,l;
    scanf("%d",&k);
    scanf("%s",s);
    l=strlen(s);
    old=s[0];
    for(i=1;i<l;++i)
    {
        if(s[i]==old)  //如果下一项与该项相同,次数就加1 
        { 
            ++t;
            if(t==k)    //如果次数已达到k次,就输出结束 
            {
                cout<<s[i];
                return 0;
            } 
        }
        else t=1;        
        old=s[i];
    }
    printf("No\n");
    return 0;    
}
点击查看AC代码

1149:最长单词2

#include<iostream>
#include<string>
#include<cstring>
#include<bits/stdc++.h>
using namespace std;
int main()
{
    string s,max;
    int maxn=0,f=0,l;
    getline(cin,s,'.');
    for(int i=0;i<=s.size();i++)
        if(s[i]==32||s[i]==0)
        {
            l=i-f;
            if(l>maxn)
            {
                maxn=l;
                max=s.substr(f,l); 
            }
            f=i+1;
        }
    cout<<max;
    return 0;
}
点击查看AC代码

第六章 函数

第一节 函数

1150:求正整数2和n之间的完全数

#include<iostream>
using namespace std;

int main(){
    int m,n,ans;
    cin>>m;
    for(int n=2;n<=m;n++) 
    {
        ans=1;
        for(int i=2;i<=n/2;i++)
            if(n%i==0)ans+=i;
        if(ans==n)cout<<n<<endl;        
    }
    return 0;
}
点击查看AC代码

1151:素数个数

#include<iostream>
using namespace std;
bool pri(int n)
{
    for(int i=2;i<=n/i;i++)
        if(n%i==0)return false;
    return true;
}
int main(){
    int n,ans=0;
    cin>>n;
    for(int i=2;i<=n;i++)
        if(pri(i))ans++;
    cout<<ans;
    return 0;
}
点击查看AC代码

1152:最大数max(x,y,z)

#include<iostream>
#include<iomanip>
using namespace std;
int max2(int a,int b)
{
    if(a>=b)return a;
    else return b;
}
int max(int a,int b,int c)
{
    return max2(max2(a,b),c); 
}
int main(){
    int a,b,c;
    cin>>a>>b>>c;
    cout<<fixed<<setprecision(3)<<1.0*max(a,b,c)/max(a+b,b,c)/max(a,b,b+c); 
    return 0;
}
点击查看AC代码

1153:绝对素数

#include<iostream>
using namespace std;
bool pri(int n)
{
    for(int i=2;i<=n/i;i++)
        if(n%i==0)return false;
    return true;
}
int retu(int n)
{
    return n%10*10+n/10;
}
int main(){
    for(int i=11;i<98;i++) 
    if(pri(i)&&pri(retu(i))) cout<<i<<endl;
    return 0;
}
点击查看AC代码

1154:亲和数

#include<iostream>
using namespace std;
int pm(int n)
{
    int ans=1;
    for(int i=2;i<n;i++)
        if(n%i==0)ans+=i;
    return ans;
}
int main(){
    for(int i=3;;i++)
        if(pm(i)!=i&&pm(pm(i))==i)
        {
            cout<<i<<' '<<pm(i); 
            break;
        }
    return 0;
}
点击查看AC代码

1155:回文三位数

#include<iostream>
using namespace std;
bool hw(int i)
{
    return i/100==i%10;
}
bool pri(int n)
{
    for(int i=2;i<=n/i;i++)
        if(n%i==0)return false;
    return true;
}
int main(){
    for(int i=101;i<=999;i++)
        if(pri(i)&&hw(i))cout<<i<<endl;
    return 0;
}
点击查看AC代码

1156:求π的值

#include<iostream>
#include<iomanip>
#include<cmath>
using namespace std;
int main()
{
    double tmp,x=1.0/sqrt(3),key=0;
    int i=1;
    tmp=x;
    while(tmp>1e-6)
    {
        key+=6*tmp*(i%2?1:-1);
        tmp*=x*x*(2*i-1)/(2*i+1);
        i++;
    }
    cout<<fixed<<setprecision(10)<<key;
    return 0;
}
点击查看AC代码

1157:哥德巴赫猜想

#include<iostream>
using namespace std;
bool pri(int n)
{
    for(int i=2;i<=n/i;i++)
        if(n%i==0)return false;
    return true;
}
int main(){
    for(int i=6;i<=100;i+=2)
        for(int j=2;j<i;j++)
            if(pri(j)&&pri(i-j))
            {
                cout<<i<<'='<<j<<'+'<<i-j<<endl;
                break;
            }
    return 0;
}
点击查看AC代码

1397:简单算术表达式求值

#include<bits/stdc++.h>
using namespace std;
int a[100001];
char c[100001]; 
int main()
{
    int n,k=0;
    char ch;
    cin>>a[0];
    //while(ch=getchar())
    {
        ch=getchar();
        cin>>n;
        switch(ch)
        {
            case '*':a[k]*=n;break;
            case '/':a[k]/=n;break;
            case '%':a[k]%=n;break;
            case '+':a[++k]=n;c[k]='+';break;
            case '-':a[++k]=n;c[k]='-';break;
            default:break;
        }
    }
    for(int i=1;i<=k;i++)
        if(c[i]=='+')a[0]+=a[i];
        else a[0]-=a[i];
    cout<<a[0];
    return 0;
}
点击查看AC代码

1398:短信计费

#include<bits/stdc++.h>
using namespace std;

int main()
{
    int n,m,ans=0;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>m;
        ans+=(m+69)/70;
    } 
    cout<<fixed<<setprecision(1)<<ans/10.0;
    return 0;
}
点击查看AC代码

1399:甲流病人初筛

#include<iostream>
using namespace std;
struct pp
{
    string name;
    float tw;
    int ks;
    bool jl;
    void ip()
    {
        cin>>name>>tw>>ks;
        if(tw>=37.5&&ks)jl=true;
    }
 } p[201];
int main(){
    int n,ans=0;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        p[i].ip();
        if(p[i].jl)ans++;
    }
    for(int i=1;i<=n;i++)
        if(p[i].jl)cout<<p[i].name<<endl;
    cout<<ans;
    return 0;
}
点击查看AC代码

1400:统计单词数

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
string s,ss;
int main(){
    getline(cin,s);
    getline(cin,ss);
    for(int i=0;i<s.size();i++)if(s[i]<='Z'&&s[i]>='A')s[i]+=32;
    for(int i=0;i<ss.size();i++)if(ss[i]<='Z'&&ss[i]>='A')ss[i]+=32;
    int f=0,st=-1,n=0,sn=s.size(),ssn=ss.size() ;
    for(int i=0;i<=ssn;i++)
    {
        if(ss[i]==32||ss[i]==0)
        {
            if(f==sn&&ss.substr(i-sn,sn)==s)
            {
                n++;
                if(st<0)st=i-sn;
            }
            f=0;
        }
        else f++;        
    }
    if(st==-1)cout<<-1;
    else cout<<n<<' '<<st;
    return 0;
}
点击查看AC代码

1401:机器翻译

#include<iostream>
using namespace std;
int a[1000],b[1000]; 
int main(){
    int m,n,s=0,l=0,j,ans=0;//s代表个数,l代表位置 
    cin>>m>>n;
    for(int i=0;i<n;i++)
    {
        cin>>a[i];
        for(j=0;j<s;j++)if(b[j]==a[i])break;
        if(j==s)
        {
            ans++;
            if(s<m)b[s++]=a[i];
            else {
                b[l]=a[i];
                l++;
                if(l==m)l=0;
            }
        }        
    }
    cout<<ans;
    return 0;
}
点击查看AC代码

1402:Vigenère密码

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
int c[100];
char m[1000],n[1000];
int main(){
    string s;
    int cn,mn,t;
    cin>>s;
    cn=s.size() ;
    for(int i=0;i<cn;i++)
        c[i]=(s[i]-'A')%32;
    cin>>s;
    mn=s.size() ;
    for(int i=0;i<mn;i++)
    {
        t=s[i]-'A';
        n[i]=t/32*32+'A'+(t%32-c[i%cn]+26)%26;
    }
    cout<<n;
    return 0;
}
点击查看AC代码

1403:素数对

#include<iostream>
using namespace std;
bool pri(int n)
{
    for(int i=2;i<=n/i;i++)
        if(n%i==0)return false;
    return true;
}
int main(){
    int n,f=0;
    cin>>n;
    for(int i=3;i<=n;i+=2)
    if(pri(i)&&pri(i+2))
    {
        cout<<i<<' '<<i+2<<endl;
        f=1;
    }
    if(!f)cout<<"empty";
    return 0;
}
点击查看AC代码

1404:我家的门牌号

#include<iostream>
using namespace std;

int main(){
    int n;
    cin>>n;
    for(int i=1;i<1000;i++)
    if((i*i+i-n*2>0)&&(i*i+i-n*2)%6==0)
    {
        cout<<(i*i+i-n*2)/6<<' '<<i;
        return 0;
    }
}
点击查看AC代码

1405:质数的和与积

#include<iostream>
using namespace std;
bool pri(int n)
{
    for(int i=2;i<=n/i;i++)
        if(n%i==0)return false;
    return true;
}
int main(){
    int n;
    cin>>n;
    for(int i=n/2;i>1;i--)
    if(pri(i)&&pri(n-i))
    {
        cout<<i*(n-i);
        return 0;
    }
}
点击查看AC代码

1406:单词替换

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
string s,ss[200],ans;
int main(){
    int i;
    while(cin>>s)
    {
        ss[i]=s;
        i++;
    }
    i--;
    for(int j=0;j<i-1;j++)
    {
        if(ss[j]==ss[i-1])cout<<ss[i];
        else cout<<ss[j];
        if(j<i-2)cout<<' ';
    }
    return 0;
}
点击查看AC代码

1407:笨小猴

#include<iostream>
using namespace std;
int mx,mn=100,a[26];
bool pri(int n)
{
    if(n<2)return false;
    for(int i=2;i<=n/i;i++)
        if(n%i==0)return false;
    return true;
}
bool luck(string s)
{
    int sl=s.size() ;
    for(int i=0;i<sl;i++)
    a[s[i]-'a']++;
    for(int i=0;i<26;i++)
    {
        if(a[i]>mx)mx=a[i];
        if(a[i]<mn&&a[i])mn=a[i];
    }
    mx-=mn;
    if(pri(mx))return true;
    else return false;
}
int main(){
    string ss;
    cin>>ss;
    if(luck(ss))cout<<"Lucky Word\n"<<mx;
    else cout<<"No Answer\n0"; 
    return 0;
}
点击查看AC代码

1408:素数回文数的个数

#include<iostream>
using namespace std;
int a[100];
bool pri(int n)
{
    for(int i=2;i<=n/i;i++)
        if(n%i==0)return false;
    return true;
}
bool hw(int n)
{
    if(n<10)return true;
    int i=0;
    while(n)
    {
        a[i++]=n%10;
        n/=10;
    }
    i--;
    for(int j=0;j<=i/2;j++)
    if(a[j]!=a[i-j])return false;
    return true;
}
int main(){
    int n,ans=0;
    cin>>n;
    for(int i=11;i<=n;i++) 
        if(pri(i)&&hw(i))
        ans++;
    cout<<ans;
    return 0;
}
点击查看AC代码

1409:判决素数个数

#include<iostream>
using namespace std;
bool pri(int n)
{
    if(n<2)return false;
    for(int i=2;i<=n/i;i++)
        if(n%i==0)return false;
    return true;
}
int main(){
    int n,m,ans=0;
    cin>>n>>m;    
    for(int i=n;i<=m;i++)
    if(pri(i))ans++;
    cout<<ans<<endl;
    return 0;
}
点击查看AC代码

1410:最大质因子序列

#include<iostream>
using namespace std;
bool pri(int n)
{
    if(n<2)return false;
    for(int i=2;i<=n/i;i++)
        if(n%i==0)return false;
    return true;
}
int main(){
    int n,m;
    cin>>n>>m;
    for(int i=n;i<=m;i++)
    {
        for(int j=i;j>=2;j--)
            if(pri(j)&&!(i%j))
            {
                cout<<j;
                break;
            }
        if(i<m)cout<<','; 
    }
    return 0;
}
点击查看AC代码

1411:区间内的真素数

#include<iostream>
using namespace std;
bool pri(int n)
{
    if(n<2)return false;
    for(int i=2;i<=n/i;i++)
        if(n%i==0)return false;
    return true;
}
int dx(int n)
{
    int ans=0;
    while(n)
    {
        ans=ans*10+n%10;
        n/=10;
    }
    return ans;
}
int main(){
    int n,m,f=0;
    cin>>n>>m;
    for(int i=n;i<=m;i++)
        if(pri(i)&&pri(dx(i)))
            if(f)cout<<','<<i;
            else
            {
                cout<<i;
                f=1;
            }
    if(f==0)cout<<"No";
    return 0;
}
点击查看AC代码

1412:二进制分类

#include<iostream>
using namespace std;
bool fl(int n)
{
    int k=0,js=0,os=0,t;
    do
    {
        t=n/(1<<k);
        if(t%2)js++;
        else os++;
        k++;
    }while(n>=(1<<k));
    return js>os;
}
int main(){
    int a=0,b=0;
    for(int i=1;i<=1000;i++)
    if(fl(i))a++;
    else b++;
    cout<<a<<' '<<b;
    return 0;
}
点击查看AC代码

1413:确定进制

#include<iostream>
#include<cmath>
using namespace std;
int zh(int n,int m)
{
    int k=0,an=0;
    while(n)
    {
        an+=pow(m,k)*(n%10);
        n/=10;
        k++;
    }
    return an;
}
int mxb(int n)
{
    int mx=0;
    while(n)
    {
        if(n%10>mx)mx=n%10;
        n/=10;
    }
    return mx;
}
int main(){
    int p,q,r;
    cin>>p>>q>>r;
    
    for(int i=max(max(mxb(p),mxb(q)),mxb(r))+1;i<=40;i++)
    {
    //    cout<<zh(p,i)<<' '<<zh(q,i)<<' '<<zh(r,i)<<' '<<i<<endl;
        if(zh(p,i)*zh(q,i)==zh(r,i))
        {
            cout<<i;
            return 0;
        }
    }
        
    cout<<0;
    return 0;
}
点击查看AC代码

第二节 递归算法

1158:求1+2+3+...

#include<iostream>
using namespace std;
int sum(int n)
{
    if(n==1)return 1;
    else return n+sum(n-1);
}
int main(){
    int n;
    cin>>n;
    cout<<sum(n);
    return 0;
}
点击查看AC代码

1159:斐波那契数列

#include<iostream>
using namespace std;
int fblq(int n)
{
    if(n==1)return 0;
    if(n==2)return 1;
    return fblq(n-1)+fblq(n-2);
}
int main(){
    int n;
    cin>>n;
    cout<<fblq(n);
    return 0;
}
点击查看AC代码

1160:倒序数

#include<iostream>
using namespace std;
int retu(int n)
{
    int m=0;
    while(n)
    {
        m=m*10+n%10;
        n/=10;
    }
    return m;
}
int main(){
    int n;
    cin>>n;
    cout<<retu(n);
    return 0;
}
点击查看AC代码

1161:转进制

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
char a[1000];
void retu(int n,int m)
{
    int i=0,t;
    while(n)
    {
        t=n%m;
        a[i++]=(t>9?t-10+'A':t+'0');
        n/=m;
    }
    a[i]='\0';
    return;
 } 
int main(){
    int n,m;
    cin>>n>>m;
    retu(n,m);
    for(int i=strlen(a)-1;i>=0;i--)cout<<a[i];
    return 0;
}
点击查看AC代码

1162:字符串逆序

#include<iostream>
#include<cstring>
using namespace std;

int main(){
    string s;
    getline(cin,s,'!');
    for(int i=s.size()-1;i>=0;i-- )
    cout<<s[i];
    return 0;
}
点击查看AC代码

1163:阿克曼(Ackmann)函数

#include<iostream>
using namespace std;
int akm(int m,int n)
{
    if(m==0)return n+1;
    if(m>0&&n==0)return akm(m-1,1);
    return akm(m-1,akm(m,n-1)); 
}
int main(){
    int n,m;
    cin>>m>>n;
    cout<<akm(m,n);
    return 0;
}
点击查看AC代码

1164:digit函数

#include<iostream>
using namespace std;
int a[10001];
int main(){
    int n,k,i=0;
    cin>>n>>k;
    while(n&&i<k)
    {
        a[i++]=n%10;
        n/=10;
    }
    cout<<a[k-1];
    return 0;
}
点击查看AC代码

1165:Hermite多项式

#include<bits/stdc++.h>
using namespace std;
double hermite(int,int); 
int main()
{
    int n,x;
    cin>>n>>x;
    cout<<fixed<<setprecision(2)<<hermite(n,x);
    return 0;
}
double hermite(int n,int x)
{
    if(n==0)return 1;
    if(n==1)return 2*x;
    return 2*x*hermite(n-1,x)-2*(n-1)*hermite(n-2,x);
}
点击查看AC代码

1166:求f(x,n)

#include<iostream>
#include<cmath>
#include<iomanip>
using namespace std;
float kf(float x,int n);
int main()
{
    float x;
    int n;
    cin>>x>>n;
    cout<<fixed<<setprecision(2)<<kf(x,n);
    return 0;
}
float kf(float x,int n)
{
    if(n==1)return sqrt(1+x);
    return sqrt(n+kf(x,n-1));
}
点击查看AC代码

1167:再求f(x,n)

#include<iostream>
#include<iomanip>

using namespace std;
double f(int n,double x)
{
    if(n==1)return x/(1+x);
    return x/(n+f(n-1,x));
}
int main()
{
    int n;
    double x;
    cin>>x>>n;
    cout<<fixed<<setprecision(2)<<f(n,x);
    return 0;
}
点击查看AC代码

第二部分:基础算法

第一章 高精度计算

1307:【例1.3】高精度乘法

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
int a[101],b[101],c[201];
int main(){
    string s;
    cin>>s;
    int la=s.size(),x=0;
    for(int i=0;i<la;i++)a[la-1-i]=s[i]-'0';
    cin>>s;
    int lb=s.size();
    for(int i=0;i<lb;i++)b[lb-1-i]=s[i]-'0';
    for(int i=0;i<la;i++)
    {
        int k;
        for(int j=0;j<lb;j++)
        {
            k=i+j;
            c[k]+=a[i]*b[j]+x;
            x=c[k]/10;
            c[k]%=10;
        }
        while(x)
        {
            c[++k]=x;
            x/=10;    
        }
    }
    int kk=201;
    while(!c[kk]&&kk) kk--;
    if(kk)
    for(int i=kk;i>=0;i--)cout<<c[i];
    else cout<<c[0];
    return 0;
}
点击查看AC代码

1308:【例1.5】高精除

#include<iostream>
 
#include<cstdio>
 #include<cstring>
 using namespace std;
 int a[305],b[305],c[305],d,i;
 void init(int a[])
 {string s;
 cin>>s;
 a[0]=s.length();
 for(i=1;i<=a[0];i++)
 a[i]=s[a[0]-i]-'0';//减法倒序存储 
 }
 void print(int a[])
 {int i;
 if(a[0]==0){cout<<0<<endl;return;}
 for(i=a[0];i>0;i--)cout<<a[i];
 cout<<endl;
 return;  //函数执行完毕回到主程序 
}


 int compare(int a[],int b[])
 {int i;
  if(a[0]>b[0])  return 1;
  if(a[0]<b[0])  return-1;
  for(i=a[0];i>0;i--)//如果两数位数相等,则按位比大小 
  {if(a[i]>b[i]) return 1;
   if(a[i]<b[i])return -1;  //按位比较若该位数相同,则判断下一位 
  }
return 0;//如果返回0则表示两数相等 
 } 


 void jian(int a[],int b[])
 {
int flag,i;
flag=compare(a,b);
if(flag==0){a[0]=0;return;}
if(flag==1)
{for(i=1;i<=a[0];i++)
{
if(a[i]<b[i]){a[i+1]--;a[i]=a[i]+10;}
a[i]-=b[i];
}
while(a[0]>0&&a[a[0]]==0)a[0]--;
return;
}
 }


 void numcpy(int p[],int q[],int det)
 {
for(int i=1;i<=p[0];i++) q[i+det-1]=p[i];
q[0]=p[0]+det-1; 
//for(int i=q[0];i>0;i--) cout<<q[i];
//cout<<endl;                     打印复制后的数字,方便理解算法,此算法主要采用低位补0做减法 
 }


 void chugao(int a[],int b[],int c[])    
 {
 int i,tmp[101];
 c[0]=a[0]-b[0]+1;   //商的位数不超过被除数的位数-除数的位数+1 
 for(i=c[0];i>0;i--)  //每次循环确定某位商的的值,从高位开始 
 {memset(tmp,0,sizeof(tmp));
 numcpy(b,tmp,i);
 while(compare(a,tmp)>=0){c[i]++;jian(a,tmp);}
 }
 while(c[0]>0&&c[c[0]]==0)  c[0]--;
 return;
 } 

int main()
 {init(a);init(b);
 chugao(a,b,c);
 print(c);
 print(a);
 return 0; 
}
点击查看AC代码

1309:【例1.6】回文数(Noip1999)

#include<iostream>
#include<cstring>
using namespace std;
int n,ans,len,source[10000];
char temp[10000];
bool hw()
{
    for(int i=0;i<(len+1)/2;i++)
        if(source[i]!=source[len-1-i])return false;
    return true;
}
void turn()
{
    int jw=0;
    for(int i=0;i<(len+1)/2;i++)source[i]=source[len-1-i]=source[i]+source[len-1-i];
    for(int i=0;i<len;i++)
    {
        source[i]+=jw;
        jw=source[i]/n;
        source[i]%=n;
    }
    if(jw==1)
        source[len++]=1;
}
int main(){
    cin>>n>>temp;
    len=strlen(temp);
    for(int i=0;i<len;i++)
    {
        int tt=temp[len-1-i];
        if(tt>=97)tt-=87;
        if(tt>=65)tt-=55;
        if(tt>='0')tt-='0';
        source[i]=tt;
    }
    while(!hw()&&ans<31)
    {
        turn();
        ans++;
    }
    if(ans<30)cout<<ans<<endl;
    else cout<<"Impossible\n";
    return 0;
}
点击查看AC代码

1168:大整数加法

#include<iostream>
#include<cstring>
using namespace std;
int a[201],b[201],la,lb;
char ca[201],cb[201];
int main()
{

    cin>>ca>>cb;
    la=strlen(ca),lb=strlen(cb);
    for(int i=0;i<la;i++)
        a[la-i-1]=ca[i]-'0';    
    for(int i=0;i<lb;i++)
        b[lb-i-1]=cb[i]-'0';
    for(int i=0;i<la||i<lb;i++)
    {
        a[i]+=b[i];
        a[i+1]+=a[i]/10;
        a[i]%=10;
    }
    int i=200;
    while(a[i]==0)i--;
    for(int j=i;j>=0;j--)cout<<a[j];
    return 0;
}
点击查看AC代码

1169:大整数减法

#include<iostream>
#include<cstring>
using namespace std;
int a[201],b[201],la,lb;
char ca[201],cb[201];
int main()
{

    cin>>ca>>cb;
    la=strlen(ca),lb=strlen(cb);
    for(int i=0;i<la;i++)
        a[la-i-1]=ca[i]-'0';    
    for(int i=0;i<lb;i++)
        b[lb-i-1]=cb[i]-'0';
    for(int i=0;i<la||i<lb;i++)
    {
        a[i]+=10-b[i];
        a[i+1]+=a[i]/10-1;
        a[i]%=10;
    }
    int i=200;
    while(a[i]==0)i--;
    for(int j=i;j>=0;j--)cout<<a[j];
    return 0;
}
点击查看AC代码

1170:计算2的N次方

#include<iostream>
using namespace std;
int main()
{
    int n,a[100]={0,1},ln=1,x;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        x=0;
        for(int j=1;j<=ln;j++)
        {
            a[j]=a[j]*2+x;
            x=a[j]/10;
            a[j]%=10;
        }
        if(x)
        {
            ln++;
            a[ln]=1;
        }
    }
    for(int i=ln;i>0;i--)cout<<a[i];
    return 0;
}
点击查看AC代码

1171:大整数的因子

#include <iostream>
#include<cstring>
#include<cstdio>
using namespace std;
int a[101];
int main()
{
    string s;
    int res,ln,flag=0;
    getline(cin,s);
    ln=s.size() ;
    for(int i=0;i<ln ;i++)
    a[i]=s[i]-'0';    
    for(int j=2;j<=9;j++)
    {
        res=0;
        for(int i=0;i<ln;i++)
        {
            res=res*10+a[i];
            res%=j;
        }
        if(res==0)
        {
            if(flag==0)
            {
                cout<<j;
                flag=1;
            }
            else cout<<' '<<j;
        }
    }
    if(flag==0)cout<<"none";
    
    return 0;
}
点击查看AC代码

1172:求10000以内n的阶乘

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
int a[100001];
int main()
{
    int ln=1,n,x=0;
    cin>>n;
    a[0]=1;
    for(int i=1;i<=n;i++)
    {
        x=0;
        for(int j=0;j<ln;j++)
        {
            a[j]=a[j]*i+x;
            x=a[j]/10;
            a[j]%=10;
        }
        while(x)
        {
            a[ln++]=x%10;
            x/=10;
        }
    }
    for(int i=ln-1;i>=0;i--)cout<<a[i];
    //cout<<'\n'<<ln;1    //输出共有多少位数 
    return 0;
}
点击查看AC代码

1173:阶乘和

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
int a[10000],s[10000],la,ls=1,x;
void jc(int n)
{
    a[0]=1,la=1;
    for(int i=1;i<=n;i++)
    {
        x=0;
        for(int j=0;j<la;j++)
        {
            a[j]=a[j]*i+x;
            x=a[j]/10;
            a[j]%=10;
        }
        while(x)
        {
            a[la++]=x%10;
            x/=10;
        }
    }
    return;
}
void pl()
{
    int i,x=0;
    for(i=0;i<la||i<ls;i++)
    {
        s[i]+=a[i]+x;
        x=s[i]/10;
        s[i]%=10;
    }
    if(x)a[i]=1;
    ls=i;
    return;
}
int main()
{
    int ln=1,n,x=0;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        jc(i);
        pl();
    }
    for(int i=ls-1;i>=0;i--)cout<<s[i];
    //cout<<'\n'<<ln;1    //输出共有多少位数 
    return 0;
}
点击查看AC代码

1174:大整数乘法

#include<iostream>
#include<cstring>
#include<string>
using namespace std;
int a[1000],b[1000],c[1000];
int main()
{
    string cs,bcs;
    cin>>bcs>>cs;
    int bn=bcs.size() ,cn=cs.size() ,x=0,ln;
    for(int i=0;i<bn ;i++)a[bn-1-i]=bcs[i]-'0';
    for(int i=0;i<cn ;i++)b[cn-1-i]=cs[i]-'0';
    for(int i=0;i<bn;i++)
        for(int j=0;j<cn;j++)
            c[i+j]+=a[i]*b[j];
    int i;
    for(i=0;i<bn+cn-1;i++)
    {
        c[i]+=x;
        x=c[i]/10;
        c[i]%=10;
    }
    while(x)
    {
        c[i++]=x%10;
        x/=10;
    }
    ln=i;
    for(i=ln-1;i>=0;i--)cout<<c[i];
    return 0;
}
点击查看AC代码

1175:除以13

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
int a[101],b[101];
int main()
{
    string s;
    cin>>s;
    int ln,res=0,sn=0,t;
    ln=s.size() ;
    for(int i=ln-1;i>=0;i--)a[i]=s[i]-'0';
    for(int i=0;i<ln;i++)
    {
        res=res*10+a[i];
        b[i]=res/13;
        res%=13;
    }
    t=0;
    while(b[t]==0)t++;
    for(int i=t;i<ln;i++)cout<<b[i];
    cout<<'\n'<<res;
    return 0;
}
点击查看AC代码

第二章 数据排序

1310:【例2.2】车厢重组

#include<iostream>
using namespace std;
int a[10001];
int main()
{
    int n,fl,ans=0;
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i];
    for(int i=1;i<=n;i++)
    {
        fl=0;
        for(int j=n;j>i;j--)
            if(a[j]<a[j-1])swap(a[j],a[j-1]),fl=1,ans++;
        if(!fl)break;
    }
    //for(int i=1;i<=n;i++)cout<<a[i]<<' ';
    cout<<ans;
    return 0;
}
点击查看AC代码

1311:【例2.5】求逆序对

//1311:【例2.5】求逆序对
#include<iostream>
using namespace std;
typedef long long nt;
nt a[100005],b[100005],ans;
void gbs(nt l,nt r)
{
    if(l==r)return; 
    nt mid=(l+r)>>1;
    gbs(l,mid);
    gbs(mid+1,r);
    nt i=l,j=mid+1,k=l;
    while(i<=mid&&j<=r)
    {
        if(a[i]<=a[j])b[k++]=a[i++];
        else b[k++]=a[j++],ans+=mid-i+1;
    }
    for(nt m=i;m<=mid;m++)b[k++]=a[m];
    for(nt m=j;m<=r;m++)b[k++]=a[m];
    for(nt m=l;m<=r;m++)a[m]=b[m];
}
int main()
{
    nt n;
    cin>>n;
    for(nt i=1;i<=n;i++) cin>>a[i];
    gbs(1,n);
    cout<<ans<<endl;
    //for(int i=1;i<=n;i++) cout<<a[i]<<' ';
    return 0;
}
点击查看AC代码

1176:谁考了第k名

#include<bits/stdc++.h>
struct st
{
    int xh;
    float cj;
}stu[10001];

int main()
{
    int n,k,l;
    scanf("%d %d",&n,&k);
    for(int i=1;i<=n;i++)scanf("%d %f",&stu[i].xh,&stu[i].cj);
    for(int i=1;i<=n;i++)
    {
        l=i;
        for(int j=i+1;j<=n;j++)
            if(stu[j].cj>stu[l].cj)l=j;
                st tmp;
                tmp=stu[l];
                stu[l]=stu[i];
                stu[i]=tmp;
    }
    printf("%d %g",stu[k].xh,stu[k].cj);
    return 0;
}
点击查看AC代码

1177:奇数单增序列

#include<iostream>
using namespace std;
int a[101],b[101];
int main()
{
    int n,l=0,t;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>a[i];
        if(a[i]%2)b[++l]=a[i];
    }
    for(int i=1;i<=l;i++)
        for(int j=1;j<l;j++)
            if(b[j]>b[j+1])
            {
                t=b[j];
                b[j]=b[j+1];
                b[j+1]=t;
            }
    cout<<b[1];
    for(int i=2;i<=l;i++)cout<<','<<b[i];
    return 0;
}
点击查看AC代码

1178:成绩排序

#include<iostream>
#include<algorithm>
using namespace std;
struct queue
{
    string name;
    int scord;
}a[22];
bool cmp(queue x,queue y)
{
    if(x.scord==y.scord) return x.name<y.name;
    else return x.scord>y.scord;
}
int main()
{
    int n;
    cin>>n;
    for(int i=1;i<=n;i++)
        cin>>a[i].name>>a[i].scord;
    sort(a+1,a+1+n,cmp);    
    for(int i=1;i<=n;i++)
        //cout<<a[i].name>>" ">>a[i].scord>>endl;
        cout<<a[i].name<<" "<<a[i].scord<<endl;
    return 0;
}
点击查看AC代码

1179:奖学金

#include<bits/stdc++.h>
using namespace std;
struct st
{
    int xh,yw,sx,yy,zf;
    void inp(int n)
    {
        cin>>yw>>sx>>yy;
        xh=n;
        zf=yw+sx+yy;
    }
    bool operator > (st x)
    {
        if(zf==x.zf)
            if(yw==x.yw)return xh<x.xh;
            else return yw>x.yw;
        else return zf>x.zf;
    }
};
bool cmp(st x,st y)
{
    return x>y;
}
int main()
{
    st a[301];
    int n;
    cin>>n;
    for(int i=1;i<=n;i++)a[i].inp(i);
    sort(a+1,a+n+1,cmp);
    for(int i=1;i<=5;i++)cout<<a[i].xh<<' '<<a[i].zf<<'\n';
    return 0;
}
点击查看AC代码

1180:分数线划定

#include<iostream>
#include<algorithm>
using namespace std;
struct stu
{
    int xh,cj;
} st[10000];
bool cmp(stu a,stu b)
{
     if(a.cj!=b.cj)return a.cj>b.cj;
     else return a.xh<b.xh;
}
int main(){
    int n,m,rs,fs;
    cin>>n>>m;
    for(int i=0;i<n;i++)cin>>st[i].xh>>st[i].cj;
    sort(st,st+n,cmp);
    rs=m*1.5;
    if(rs>n)rs=n;
    fs=st[rs-1].cj;
    while(rs<n&&st[rs].cj==fs)rs++;
    cout<<fs<<' '<<rs<<'\n';
    for(int i=0;i<rs;i++)
        cout<<st[i].xh<<' '<<st[i].cj<<'\n';
    return 0;
}
点击查看AC代码

1181:整数奇偶排序

#include<iostream>
#include<algorithm>
using namespace std;
int a[10],b[10],la,lb;
bool cmp(int x,int y)
{
    return x>y;
}
int main(){
    int n;
    for(int i=0;i<10;i++)
    {
        cin>>n;
        if(n%2)a[la++]=n;
        else b[lb++]=n;
    }
    sort(a,a+la,cmp);
    sort(b,b+lb);
    for(int i=0;i<la;i++)cout<<a[i]<<' ';
    for(int i=0;i<lb-1;i++)cout<<b[i]<<' ';
    cout<<b[lb-1];
    return 0;
}
点击查看AC代码

1182:合影效果

#include<iostream>
#include<algorithm>
#include<iomanip>
using namespace std;
float a[40],b[40];
int la,lb;
bool cmp(float x,float y)
{
    return x>y;
}
int main(){
    int n;
    string s;
    cin>>n;
    for(int i=0;i<n;i++)
    {
        cin>>s;
        if(s=="male")cin>>a[la++];
        else cin>>b[lb++];
    }
    sort(a,a+la);
    sort(b,b+lb,cmp);
    for(int i=0;i<la;i++)cout<<fixed<<setprecision(2)<<a[i]<<' ';
    for(int i=0;i<lb-1;i++)cout<<fixed<<setprecision(2)<<b[i]<<' ';
    cout<<fixed<<setprecision(2)<<b[lb-1];
    return 0;
}
点击查看AC代码

1183:病人排队

#include<iostream>
#include<algorithm>
using namespace std;
struct people
{
    int xh,age;
    string id; 
} pp[100];
bool cmp(people x,people y)
{
    if(x.age!=y.age&&(x.age>=60||y.age>=60))return x.age>y.age;
    return x.xh<y.xh;
}
int main()
{
    int n;
    cin>>n;
    for(int i=0;i<n;i++)
    {
        pp[i].xh=i;
        cin>>pp[i].id>>pp[i].age;
    }
    sort(pp,pp+n,cmp);
    for(int i=0;i<n;i++)cout<<pp[i].id<<'\n';
}
点击查看AC代码

1184:明明的随机数

#include<iostream>
#include<algorithm>
using namespace std;
struct people
{
    int xh,age;
    string id; 
} pp[100];
bool cmp(people x,people y)
{
    if(x.age!=y.age&&(x.age>=60||y.age>=60))return x.age>y.age;
    return x.xh<y.xh;
}
int main()
{
    int n;
    cin>>n;
    for(int i=0;i<n;i++)
    {
        pp[i].xh=i;
        cin>>pp[i].id>>pp[i].age;
    }
    sort(pp,pp+n,cmp);
    for(int i=0;i<n;i++)cout<<pp[i].id<<'\n';
}
点击查看AC代码

1185:单词排序

using namespace std;
#include<bits/stdc++.h>
int main(){
    string s,bs[101];
    //char as[5000];
    int n=0,f=0,l;
    while(getline(cin,s))
    {    
    f=0;
    l=s.size();
    for(int i=0;i<=l;i++)
    {
        if(s[i]==' '||s[i]=='\0')
        {
            if(i>f) //如果不是连续空格就取出前一个字符串 
                bs[n++]=s.substr(f,i-f);
            f=i+1; //当前字符为空格,有效字符串只可能是下一位 开始 
        }    
    }
    }
    //while(cin>>bs[f++]); 
    sort(bs,bs+n);//相同单词应排在相邻位置 
    s=bs[0];
    cout<<s;
    for(int i=1;i<n;i++)
    {
        if(bs[i]!=s)cout<<'\n'<<bs[i];
        s=bs[i];//s用来记录每次输出的前一个单词,如果跟当单词一样就不输出 
    }
    cout<<endl;
    return 0;
}
点击查看AC代码

1186:出现次数超过一半的数

#include<iostream>
using namespace std;
int a[101];
int main(){
    int n,t;
    cin>>n;
    for(int i=0;i<n;i++)
    {
        cin>>t;
        a[t+50]++;
    }
    for(int i=0;i<101;i++)
        if(a[i]>n/2)
        {
            cout<<i-50 ;
            return 0;
        }
    cout<<"no";
    return 0;
}
点击查看AC代码

1187:统计字符数

#include<iostream>
using namespace std;
int a[26];
int main(){
    string s;    
    int ch,n,max,maxn=0;
    cin>>s;
    n=s.size() ;
    for(int i=0;i<n;i++)
    {
        ch=s[i]-'a';
        a[ch]++;
        if(a[ch]>maxn||a[ch]==maxn&&ch<max)maxn=a[ch],max=ch;
    }
    cout<<char(max+'a')<<' '<<maxn;
    return 0;
}
点击查看AC代码

第三章 递推算法

1312:【例3.4】昆虫繁殖

#include<iostream>
using namespace std;
long long a[50];
int main(){
    a[0]=1;
    int x,y,z;
    cin>>x>>y>>z;
    for(int i=1;i<x+2;i++)a[i]=1;
    for(int i=x+2;i<=z;i++)a[i]=a[i-1]+a[i-x-2]*y;
    cout<<a[z];
    return 0;
}
点击查看AC代码

1313:【例3.5】位数问题

#include<iostream>
using namespace std;
int js[1001],os[1001];
int ws(int n)
{
    js[1]=1,os[1]=8;
    for(int i=2;i<=n;i++)
    js[i]=(os[i-1]+js[i-1]*9)%12345,os[i]=(os[i-1]*9+js[i-1])%12345;
    return os[n];
}
int main(){
    int n;
    cin>>n;
    if(n==1)cout<<9;
    else cout<<ws(n); 
    return 0;
}
点击查看AC代码

1314:【例3.6】过河卒(Noip2002)

#include<bits/stdc++.h>
using namespace std;
    long long a[25][25];//(x,y)代表马的位置,(n,m)代表目标位置 
//为方便输入马的控制位置,所有坐标均向右向下平移2单位 
int main(){
    std::ios::sync_with_stdio(false);
    int x,y,n,m;
    cin>>n>>m>>x>>y;
    for(int i=2;i<=n+2;i++)
        for(int j=2;j<=m+2;j++)
            a[i][j]=1;
    for(int i=0;i<=n+4;i++)a[i][1]=0;
    for(int j=0;j<=m+4;j++)a[1][j]=0;
    a[x][y+1]=a[x][y+3]=a[x+1][y]=a[x+1][y+4]=0;      //对方马控制的8个点 
    a[x+3][y]=a[x+3][y+4]=a[x+4][y+1]=a[x+4][y+3]=0;  //对方马控制的8个点
    a[x+2][y+2]=0;
    a[2][1]=1;
    for(int i=2;i<=n+2;i++)
        for(int j=2;j<=m+2;j++)
            if(a[i][j]!=0)a[i][j]=a[i-1][j]+a[i][j-1];
    cout<<a[n+2][m+2]; 
    return 0;
}
点击查看AC代码

1188:菲波那契数列(2)

#include<iostream>
using namespace std;
int a[1000001],b[100];
int main(){
    int n,max=0;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>b[i];
        if(b[i]>max)max=b[i];
    }
    a[1]=a[2]=1;
    for(int i=3;i<=max;i++)
    a[i]=(a[i-1]+a[i-2])%1000;
    for(int i=1;i<=n;i++)cout<<a[b[i]]<<'\n';
    
    return 0;
}
点击查看AC代码

1189:Pell数列

#include<iostream>
using namespace std;
const int MAXN=1000005,M=32767;
int fbnc[MAXN];
int fb(int n){
    if(!fbnc[n])fbnc[n]=(fb(n-2)+2*fb(n-1))%M;
    return fbnc[n];
}
int main(){    
    int n,x;        
    fbnc[1]=1,fbnc[2]=2;
    cin>>n;
    for(int i=0;i<n;i++){
        cin>>x;
        cout<<fb(x)<<endl;
    }    
    return 0;
}
点击查看AC代码

1190:上台阶

#include<iostream>
using namespace std;
long long a[101];
int b[10000];
int main(){
    int n=1,m,max=0;
    while(cin>>m&&m!=0)
    {
        b[n]=m;
        if(b[n++]>max)max=b[n-1];
    }
    a[1]=1;
    a[2]=2;
    a[3]=4;
    for(int i=4;i<=max;i++)
    a[i]=a[i-1]+a[i-2]+a[i-3];
    for(int i=1;i<n;i++)cout<<a[b[i]]<<'\n';
    
    return 0;
}
点击查看AC代码

1191:流感传染

#include<iostream>
using namespace std;
int a[101][101];
int main(){
    int n,num=0,m;
    char ch;
    cin>>n;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
        {
            cin>>ch;
            if(ch=='.')a[i][j]=1;//健康 
            else if(ch=='#')a[i][j]=0;//
            else a[i][j]=2,num++;//病人 
        }
    cin>>m;
    for(int i=2;i<=m;i++)
        for(int j=1;j<=n;j++)
            for(int k=1;k<=n;k++)
            {
                if(a[j][k]==2)
                {
                    if(a[j-1][k]==1)a[j-1][k]=2,num++;
                    if(a[j][k-1]==1)a[j][k-1]=2,num++;
                    if(a[j+1][k]==1)a[j+1][k]=3,num++;
                    if(a[j][k+1]==1)a[j][k+1]=3,num++;
                }
                if(a[j][k]==3)a[j][k]=2;
             }
    cout<<num; 
    return 0;
}
点击查看AC代码

1192:放苹果

#include<iostream>
using namespace std;
int a[100][100],b[100][2];
long long fp1(int n,int m)
{
    if(a[n][m])return a[n][m];
    if(m==1||n==1||n==0)a[n][m]=1;
    else if(n<m)a[n][m]=fp1(n,n);
    else if(n>=m)a[n][m]=fp1(n,m-1)+fp1(n-m,m);
    return a[n][m];
}
int main(){
    int n;
    cin>>n;
    for(int i=1;i<=n;i++)cin>>b[i][0]>>b[i][1];
    for(int i=1;i<=n;i++)cout<<fp1(b[i][0],b[i][1])<<endl;    
    return 0;
}
点击查看AC代码

1193:吃糖果

#include<iostream>
using namespace std;
long long a[101];
int main(){
    int n;
    cin>>n;    
    a[1]=1;
    a[2]=2;
    for(int i=3;i<=n;i++)
    a[i]=a[i-1]+a[i-2];
    cout<<a[n]<<'\n';    
    return 0;
}
点击查看AC代码

1194:移动路线

#include<iostream>
using namespace std;
int a[100][100];

int main(){
    int n,m;
    cin>>n>>m;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)
            if(i==1||j==1)a[i][j]=1;
            else a[i][j]=a[i-1][j]+a[i][j-1];
    cout<<a[n][m];    
    return 0;
}
点击查看AC代码

1195:判断整除

#include<iostream>
using namespace std;
int a[10001],b[10001][101],k,n;
int main(){
    cin>>n>>k;
    for(int i=1;i<=n;i++)cin>>a[i];
    b[0][0]=1;
    for(int i=1;i<=n;i++)
        for(int j=0;j<k;j++)
            b[i][j]=b[i-1][(j+a[i]%k)%k]||b[i-1][(k+j-a[i]%k)%k];
    if(b[n][0])cout<<"YES";
    else cout<<"NO";
    return 0;
}
点击查看AC代码

1196:踩方格

#include<iostream>
using namespace std;
int ans=0,a[30][50],fx[3][2]={{1,0},{0,-1},{0,1}};
void dfs(int x,int y,int p)
{
    if(p<1)return;
    int tx,ty;
    a[x][y]=1;//表示己 
    for(int i=0;i<3;i++)
    {        
        tx=x+fx[i][0],ty=y+fx[i][1];
        if(a[tx][ty]==0)
        {
            if(p==1)ans++; 
            dfs(tx,ty,p-1);
            a[tx][ty]=0;
        }
    }
    return;
}
int main()
{
    int n;
    cin>>n;
    dfs(1,25,n);
    cout<<ans;
     return 0;
}
点击查看AC代码

1197:山区建小学

#include<iostream>
#include<string.h>
using namespace std;
int dp[501][501],a[501],mi[501][501];
int m,n;
int main()
{
    int i,j,x,k;
    cin>>m>>n;
    a[1]=0;
    for (i=2;i<=m;i++)
    {
        cin>>x;
        a[i]=a[i-1]+x;
    }
    for (i=0;i<=m;i++)
        mi[i][i]=0;
    for (i=1;i<=m;i++)
        for (j=i+1;j<=m;j++)
            mi[i][j]=mi[i][j-1]+a[j]-a[(i+j)/2];
    for (i=1;i<=m;i++)
        for (j=1;j<=n;j++)
            dp[i][j]=250000;
    for (i=1;i<=m;i++)
        dp[i][1]=mi[1][i];
    for (i=2;i<=m;i++)
        for (j=2;j<=n;j++)
            for (k=j-1;k<i;k++)
                dp[i][j]=min(dp[i][j],dp[k][j-1]+mi[k+1][i]);
    cout<<dp[m][n]<<endl;
    return 0;
}
点击查看AC代码

第四章 递归算法

1315:【例4.5】集合的划分

#include<bits/stdc++.h>
using namespace std;
long long hs(int n,int m)
{
    if(n<m)return 0;
    if(n==m)return 1;
    if(m==1)return 1;
    return hs(n-1,m-1)+m*hs(n-1,m);
}
int main()
{
    int n,m;
    cin>>n>>m;
    cout<<hs(n,m);
    return 0;
}
点击查看AC代码

1316:【例4.6】数的计数(Noip2001)

#include<bits/stdc++.h>
using namespace std;
int a[1000];
int dfs(int n)
{
    if(a[n]==0)
    {
        a[n]=1;
        for(int i=1;i<=n/2;i++)
        a[n]+=dfs(i);
    }
    return a[n];
}
int main()
{
    int n;
    cin>>n;
    a[1]=1;
    cout<<dfs(n); 
    return 0;
}
点击查看AC代码

1198:逆波兰表达式

#include <bits/stdc++.h>
using namespace std;
double f[1000];
char s[1000];
double js()
{
    cin>>s;
    if (s[0]=='*') return js()*js();
    else if (s[0]=='/') return js()/js();
         else if (s[0]=='-') return js()-js();
              else if (s[0]=='+') return js()+js();
                   else return atof(s);
}
int main()
{
    printf("%lf\n",js());
    return 0;
}
点击查看AC代码

1199:全排列

#include<iostream>
using namespace std;
string s;
int b[27],p[27],l;
void pr()
{
    for(int i=1;i<=l;i++)
        cout<<s[b[i]];
    cout<<endl;
    return;
}
void dfs(int dp)
{
    if(dp==l+1)
    {
        pr();
        return;
    }
    for(int i=0;i<l;i++)//i为序号 
    {
        if(p[i]==0)
        {
            b[dp]=i;
            p[i]=1;
            dfs(dp+1);
            p[i]=0;
        }
    
    }
}
int main()
{
    cin>>s;
    l=s.size() ;
    b[0]=-1;
    dfs(1);
     return 0;
}
点击查看AC代码

1200:分解因数

#include<iostream>
using namespace std;
int a[1000],ans;
void fj(int x,int n)
{
    ans++;
    for(int i=n;i<=x/i;i++)
        if(x%i==0)fj(x/i,i);
    return ;
}
int main()
{
    int n;
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i]; 
    for(int i=1;i<=n;i++)
    {
        ans=0;
        fj(a[i],2);
        cout<<ans<<endl;
    }
     return 0;
}
点击查看AC代码

1201:菲波那契数列

#include<iostream>
using namespace std;
int a[21],b[10000];
int main()
{
    int n,max=0;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>b[i];
        if(max<b[i])max=b[i];
    }
    a[1]=1,a[2]=1;
    for(int i=3;i<=max;i++)a[i]=a[i-1]+a[i-2];
    for(int i=1;i<=n;i++)cout<<a[b[i]]<<endl;    
     return 0;
}
点击查看AC代码

1202:Pell数列

#include<iostream>
using namespace std;
int a[1000001],b[100];
int main()
{
    int n,max=0;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>b[i];
        if(max<b[i])max=b[i];
    }
    a[1]=1,a[2]=2;
    for(int i=3;i<=max;i++)a[i]=(2*a[i-1]+a[i-2])%32767;
    for(int i=1;i<=n;i++)cout<<a[b[i]]<<endl;    
     return 0;
}
点击查看AC代码

1203:扩号匹配问题

#include<bits/stdc++.h>
using namespace std;
char m[101][101];
char* pp(char arr[])
{
    char tmp[101];
    char *ans=new char[101];
    int t[101];
    int l=strlen(arr),top=0;
    for(int i=0;i<l;i++)
    {
        ans[i]=' ';
        if(arr[i]=='(') 
            tmp[++top]='(',t[top]=i;
        else if(arr[i]==')')
            if(tmp[top]=='(')top--;
            else ans[i]='?';
        else ans[i]=' ';
    }
    while(top>0)
    {
        ans[t[top--]]='$';
    }
    ans[l]='\0';
    return ans;
} 
int main()
{
    int i=0;
    while(gets(m[i++]));
    for(int j=0;j<i;j++)
    {
        cout<<m[j]<<endl;
        cout<<pp(m[j])<<endl;
    }
     return 0;
}
点击查看AC代码

1204:爬楼梯

#include<iostream>
using namespace std;
int a[31],b[10001];
int main()
{    
    int n=0,maxn=0;
    while(cin>>b[n])
    {
        if(maxn<b[n]) maxn=b[n];
        n++;
    }
    a[1]=1,a[2]=2;
    for(int i=3;i<=maxn;i++)
        a[i]=a[i-1]+a[i-2];
    for(int i=0;i<n;i++)cout<<a[b[i]]<<endl;
     return 0;
}
点击查看AC代码

1205:汉诺塔问题

#include<cstdio>
void hnt(int n,char x,char y,char z)
{
    if(n==1)printf("%c->1->%c\n",x,y);
    else
    {
        hnt(n-1,x,z,y);
        printf("%c->%d->%c\n",x,n,y);
        hnt(n-1,z,y,x);
    }
}
int main()
{
    int n;
    char x,y,z;
    scanf("%d %c %c %c",&n,&x,&y,&z);
    hnt(n,x,y,z);
    return 0;
}
点击查看AC代码

1206:放苹果

#include<iostream>
using namespace std;
int a[100][100],b[100][2];
long long fp1(int n,int m)
{
    if(a[n][m])return a[n][m];
    if(m==1||n==1||n==0)a[n][m]=1;
    else if(n<m)a[n][m]=fp1(n,n);
    else if(n>=m)a[n][m]=fp1(n,m-1)+fp1(n-m,m);
    return a[n][m];
}
int main(){
    int n;
    cin>>n;
    for(int i=1;i<=n;i++)cin>>b[i][0]>>b[i][1];
    for(int i=1;i<=n;i++)cout<<fp1(b[i][0],b[i][1])<<endl;    
    return 0;
}
点击查看AC代码

1207:求最大公约数问题

#include<iostream>
using namespace std;

int main()
{
    int n,m;
    cin>>n>>m;
    while(m)
    {
        int tmp=n;
        n=m;
        m=tmp%n;
    }
    cout<<n;
     return 0;
}
点击查看AC代码

1208:2的幂次方表示

#include<iostream>
#include<cmath>
using namespace std;
string pp(int n)
{
    if(n==1)return "2(0)";
    if(n==2)return "2"; 
    if(n==3)return "2+2(0)";
    int p=0;
    while(n/2>=pow(2,p))p++;
    if(n==pow(2,p))return "2("+pp(p)+")";
    else return "2("+pp(p)+")+"+pp(n-pow(2,p));
 } 
int main()
{
    int n;
    cin>>n;
    cout<<pp(n);
     return 0;
}
点击查看AC代码

1209:分数求和

#include<cstdio>
using namespace std;
int a[100][2];
int gcd(int n,int m)
{
    while(m)
    {
        int tm=n;
        n=m;
        m=tm%n;
    }
    return n;
}
void plu(int &n,int &m,int x,int y)
{
    n=n*y+x*m;
    int tmp=gcd(n,m*y);
    n/=tmp;
    m=m*y/tmp;
}
int main()
{
    int n;
    scanf("%d",&n);
    for(int i=0;i<n;i++)scanf("%d/%d",&a[i][0],&a[i][1]);
    for(int i=1;i<n;i++)plu(a[0][0],a[0][1],a[i][0],a[i][1]);
    if(a[0][1]!=1)printf("%d/%d",a[0][0],a[0][1]);
    else printf("%d",a[0][0]);
     return 0;
}
点击查看AC代码

1210:因子分解

#include<iostream>
using namespace std;

int main()
{
    int n,k=2,m,f=0;
    cin>>n;
    while(n>1)
    {
        m=0;
        while(n%k==0)
        {
            m++;
            n/=k;
        }
        if(m>=1)
            if(f==0)
            {
                cout<<k;
                f=1;
            }
            else cout<<"*"<<k;
        if(m>1)cout<<'^'<<m;
        k++;
    }
     return 0;
}
点击查看AC代码

1211:判断元素是否存在

#include<cstdio>
int a[100001],a2[100001],a3[100001],t,t2=1,t3=1,h2=1,h3=1;
int main(){
    int n,x,tx2,tx3;
    scanf("%d,%d",&n,&x);
    a[0]=1,a2[0]=1,a3[0]=1;
    while(a[t]<x)
    {
        a2[t2++]=2*a[t]+1,a3[t3++]=3*a[t]+1;
        t++; 
        if(a2[h2]<a3[h3])a[t]=a2[h2++];
        else if(a2[h2]>a3[h3])a[t]=a3[h3++];
        else 
        {
            a[t]=a2[h2++];
            h3++;
        }
    }
    if(a[t]==x)printf("YES");
    else printf("NO");
    return 0;
}
点击查看AC代码

第五章 搜索与回溯算法

1317:【例5.2】组合的输出

#include<iostream>
#include<iomanip>
using namespace std;
int n,r,a[21];
void pr()
{
    for(int i=1;i<=r;i++)cout<<fixed<<setw(3)<<a[i];
    cout<<endl;
    return;
}
void dfs(int star,int dp)
{
    //边界
    if(dp==r+1)
    {
        pr();
        return;
    }
    //递推 
    for(int i=star;i<=n;i++)
    {
        a[dp]=i;
        star=i+1;
        dfs(star,dp+1);
    }
}
int main()
{
    cin>>n>>r;
    dfs(1,1);
    return 0;
}
点击查看AC代码

1318:【例5.3】自然数的拆分

#include<bits/stdc++.h>
using namespace std;
int a[10001],n;
void print(int step)

{

    cout<<n<<"=";

    for(int i=1;i<step;i++)

        cout<<a[i]<<"+";

    cout<<a[step]<<endl;

}
void dfs(int c,int step)
{
    for(int i=a[step-1];i<=c;i++)
      {
      if(i<n) 
      {
          a[step]=i;
          c=c-i;
          if(c==0)
          print(step);
          else   dfs(c,step+1);
          c=c+i;
      }
}
}

int main()
{  
 for(int i=0;i<1001;i++)
          a[i]=1;
    cin>>n;
    dfs(n,1);
    return 0;
}
点击查看AC代码

1212:LETTERS

#include<iostream>
#include<cstdio>
using namespace std;
int a[22][22],b[27],ans=0;
int fx[4][2]={{1,0},{-1,0},{0,1},{0,-1}};
void dfs(int x,int y,int dp)
{
    int tx,ty;
    if(dp>ans)ans=dp;
    b[a[x][y]]=1;
    for(int i=0;i<4;i++)
    {
        tx=x+fx[i][0];
        ty=y+fx[i][1];
        if(b[a[tx][ty]]==0)
        {
            dfs(tx,ty,dp+1);
            b[a[tx][ty]]=0;
        }
    }
}
int main(){
    int r,c;
    char ch;
    scanf("%d %d",&r,&c);
    for(int i=1;i<=r;i++)
        for(int j=1;j<=c;j++)
        {
            cin>>ch;
            a[i][j]=ch-'A'+1;
        }
    b[0]=1;
    dfs(1,1,1);
    printf("%d",ans);
    return 0;
}
点击查看AC代码

1213:八皇后问题

#include<iostream>
#include<iomanip>
using namespace std;
int b[9],ans=1;
void pr()
{
    cout<<"No. "<<ans++<<endl;
    for(int i=1;i<9;i++)
    {
        for(int j=1;j<9;j++)
        {
            if(b[j]==i)cout<<1;
            else cout<<0;
            if(j<8)cout<<' ';
        }
        cout<<endl;
    }
}
bool jc(int n,int y)
{
    for(int i=1;i<n;i++)
    {
        if(b[i]==y)return false;
        if(i+b[i]==n+y)return false;
        if(i-b[i]==n-y)return false;
    }
    return true;
}
void qk(int n)
{
    if(n==9)pr();
    for(int i=1;i<9;i++)
    {
        if(jc(n,i))
        {
            b[n]=i;
            qk(n+1);
            b[n]=0;
        }
        
    }
    return;
 } 
int main(){
    qk(1); 
    return 0;
}
点击查看AC代码

1214:八皇后

#include<iostream>
#include<iomanip>
using namespace std;
int b[9],ans=0,a[93],c[1000];
bool jc(int n,int y)
{
    for(int i=1;i<n;i++)
    {
        if(b[i]==y)return false;
        if(i+b[i]==n+y)return false;
        if(i-b[i]==n-y)return false;
    }
    return true;
}
void qk(int n)
{
    if(n==9)
    {
        ans++;
        int num=0;
        for(int i=1;i<9;i++)num=num*10+b[i];
        a[ans]=num;
        return;
    }
    for(int i=1;i<9;i++)
    {
        if(jc(n,i))
        {
            b[n]=i;
            qk(n+1);
            b[n]=0;
        }
        
    }
    return;
 } 
int main(){
    qk(1);
    int n;
    cin>>n;
    for(int i=1;i<=n;i++)cin>>c[i];
    for(int i=1;i<=n;i++)cout<<a[c[i]]<<endl; 
    return 0;
}
点击查看AC代码

1215:迷宫

#include<iostream>
#include<cstring>
using namespace std;
int a[102][102],b[1000],n,ha,la,hb,lb,m;
int fx[4][2]={{1,0},{-1,0},{0,1},{0,-1}};
int dfs(int x,int y)
{
    if(x==hb&&y==lb)return 1;
    a[x][y]=0;
    int tx,ty;
    for(int i=0;i<4;i++)
    {
        tx=x+fx[i][0];
        ty=y+fx[i][1];
        if(a[tx][ty])
            if(dfs(tx,ty))return 1;
    }
    return 0;
}
int main(){
    cin>>n;
    char ch;
    for(int i=1;i<=n;i++)
    {
        cin>>m;
        memset(a,0,sizeof(a));
        for(int j=1;j<=m;j++)
            for(int k=1;k<=m;k++)
            {
                cin>>ch;
                if(ch=='.')a[j][k]=1;
            }
        cin>>ha>>la>>hb>>lb;
        ha++,la++,hb++,lb++;
        if(a[ha][la]==0||a[hb][lb]==0)b[i]=0;
        else b[i]=dfs(ha,la);
    }
    for(int i=1;i<=n;i++)
    {        
        if(b[i])cout<<"YES\n";
        else cout<<"NO\n";
    }
    return 0;
}
点击查看AC代码

1216:红与黑

#include<iostream>
#include<cstring>
using namespace std;
int a[102][102],b[1000],l,n,ha,la,m,ans;
int fx[4][2]={{1,0},{-1,0},{0,1},{0,-1}};
void dfs(int x,int y)
{
    ans++;
    a[x][y]=0;
    int tx,ty;
    for(int i=0;i<4;i++)
    {
        tx=x+fx[i][0];
        ty=y+fx[i][1];
        if(a[tx][ty])dfs(tx,ty);
    }
    return;
}
int main(){
    do
    {
        cin>>m>>n;
        if(m==0&&n==0)break;
        char ch;
        ans=0;
        memset(a,0,sizeof(a));
        for(int j=1;j<=n;j++)
            for(int k=1;k<=m;k++)
            {
                cin>>ch;
                if(ch=='.')a[j][k]=1;
                if(ch=='@')ha=j,la=k;
            }        
        dfs(ha,la);
        b[l++]=ans;
    }while(1);
    for(int i=0;i<l;i++)cout<<b[i]<<'\n';
    return 0;
}
点击查看AC代码

1217:棋盘问题

#include<iostream>
#include<cstring>
using namespace std;
int a[102][102],b[1000],c[10][2],l,n,m,ans;
bool check(int y,int p)
{
    for(int i=1;i<p;i++)
        if(c[i][1]==y)return false;
    return true;
}
void dfs(int h,int dp)
{
    if(dp==m+1)
    {
        ans++;
        return;
    }
    for(int i=h;i<=n;i++)
    for(int j=1;j<=n;j++)
        {
            if(check(j,dp)&&a[i][j])
            {
                c[dp][0]=i,c[dp][1]=j;
                dfs(i+1,dp+1);
                c[dp][0]=0,c[dp][1]=0;
            }
        }
    return;
}
int main(){
    do
    {
        cin>>n>>m;
        if(m==-1&&n==-1)break;
        char ch;
        ans=0;
        memset(a,0,sizeof(a));
        memset(c,0,sizeof(c));
        for(int j=1;j<=n;j++)
            for(int k=1;k<=n;k++)
            {
                cin>>ch;
                if(ch=='#')a[j][k]=1;
            }        
        dfs(1,1);
        b[l++]=ans;
    }while(1);
    for(int i=0;i<l;i++)cout<<b[i]<<'\n';
    return 0;
}
点击查看AC代码

1218:取石子游戏

#include<iostream>
using namespace std;
int a[10000],l;
int main(){
    int n,m;
    do
    {
        cin>>n>>m;
        if(!(n|m))break;
        if(n<m)swap(n,m);
        if(n/m>=2||n%m==0)a[l++]=1;
        else 
        {
            int k=1;
            while(n/m<2&&n%m)
            {
                int tmp=m;
                m=n%m;
                n=tmp;
                k++;
            }
            if(k%2)a[l++]=1;
            else a[l++]=0;
        }
    }while(1);
    for(int i=0;i<l;i++)
        if(a[i])cout<<"win\n";
        else cout<<"lose\n";
    return 0;
}
点击查看AC代码

1219:马走日

#include<bits/stdc++.h>
using namespace std;
int f[8][2]={{1,-2},{2,-1},{2,1},{1,2},{-1,2},{-2,1},{-2,-1},{-1,-2}};
int a[11][11]; 
int T;
int n,m,x,y;
int ans;
void research(int x,int y,int dep)
{
    if(dep==n*m)
    {
        ans++; 
        return;
    }
    else
    {
        for(int i=0;i<8;i++)
        {
            int x1=x+f[i][0];
            int y1=y+f[i][1];
            if(x1>=1&&x1<=n&&y1>=1&&y1<=m&&a[x1][y1]==0)
            {
            a[x1][y1]=1;
            research(x1,y1,dep+1);
            a[x1][y1]=0;    
            }
        }
        
         
    }
}
int main()
 { 
   cin>>T;
  for(int i=1;i<=T;i++) 
 {   memset(a,0,sizeof(a));
      ans=0;
     cin>>n>>m>>x>>y;
     x++;y++;
     a[x][y]=1;
     research(x,y,1);
 printf("%d\n",ans);
 }
    return 0;
}
点击查看AC代码

1220:单词接龙

#include<bits/stdc++.h>
using namespace std;
string ss[1001],ms;
int p[1001],maxn,n;
bool kjl(string s1,string s2,int n)
{
    int l1=s1.size(),l2=s2.size();
    if(n>l1||n>l2)return false;
    for(int i=0;i<n;i++)
        if(s1[l1-1-i]!=s2[n-1-i])return false;
    return true;
}
int jl(string s1,string s2) 
{
    int l1=s1.size(),l2=s2.size();
    for(int i=1;i<l1&&i<l2;i++)
    if(kjl(s1,s2,i))return i;
    return 0;
}
void dfs(string s)
{
    int l1=s.size();
    if(maxn<l1)maxn=l1;
    for(int i=1;i<=n;i++)
    {
        int tt= jl(s,ss[i]); 
        if(p[i]<2&&tt>0)
        {
            p[i]++;
            dfs(s.substr(0,l1-tt)+ss[i]);
            p[i]--;
        }
    }
} 
int main()
{
    char ch;
    cin>>n;
    for(int i=1;i<=n;i++)cin>>ss[i];
    cin>>ch;
    for(int i=1;i<=n;i++)
        if(ss[i][0]==ch)
        {
            p[i]=1;
            dfs(ss[i]);
            p[i]=0;
        }
    cout<<maxn;
    return 0;
}
点击查看AC代码

1221:分成互质组

#include<iostream>
using namespace std;
int n,a[100],b[100][100],c[100],ans=1;
int gcd(int n,int m)
{
    while(m)
    {
        int mp=n;
        n=m;
        m=mp%n;
    }
    return n;
}
int main()
{
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i];
    b[1][1]=a[1];
    c[1]=1;
    for(int i=2;i<=n;i++)
    {
        int ok;
        for(int j=1;j<=ans;j++)
        {
            ok=1;
            for(int k=1;k<=c[j];k++)
                if(gcd(b[j][k],a[i])>1)
                {
                    ok=0;
                    break;
                }
            if(ok)
            {
                c[j]++;
                b[j][c[j]]=a[i];
                break;
            }
        }
        if(ok==0)
        {
            ans++;
            b[ans][1]=a[i];
            c[ans]=1;
        }
    }
    cout<<ans;
    return 0;
}
点击查看AC代码

1222:放苹果

#include<iostream>
using namespace std;
int a[100][100],b[100][2];
long long fp1(int n,int m)
{
    if(a[n][m])return a[n][m];
    if(m==1||n==1||n==0)a[n][m]=1;
    else if(n<m)a[n][m]=fp1(n,n);
    else if(n>=m)a[n][m]=fp1(n,m-1)+fp1(n-m,m);
    return a[n][m];
}
int main(){
    int n;
    cin>>n;
    for(int i=1;i<=n;i++)cin>>b[i][0]>>b[i][1];
    for(int i=1;i<=n;i++)cout<<fp1(b[i][0],b[i][1])<<endl;    
    return 0;
}
点击查看AC代码

第六章 贪心算法

1319:【例6.1】排队接水

#include<bits/stdc++.h>
using namespace std;
int a[1010],b[1010],n;
int sum=0,num;
int main()
{   int t;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>a[i];
        b[i]=i;
    }
     for(int i=1;i<=n-1;i++)
        for(int j=1;j<=n-i;j++)
        {
            if(a[j]>a[j+1]) 
             {
               swap(a[j],a[j+1]);
               swap(b[j],b[j+1]);
             }       
        }
        for(int i=1;i<=n;i++)
        {
            num=0;
            for(int j=i-1;j>=1;j--)
            {
                num=num+a[j];
            }
            sum=sum+num;
        }
        for(int i=1;i<=n;i++)
            printf("%d ",b[i]);
        printf("\n%.2f",1.0*sum/n);
        return 0;
}
点击查看AC代码

1320:【例6.2】均分纸牌(Noip2002)

#include<iostream>
using namespace std;
int a[105];
int num=10000,ans=0;
int main()
{
    int n,sum=0,w;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>a[i];
        sum+=a[i];
    }
    int b=sum/n;
    for(int i=1;i<=n;i++)
    {
        if(a[i]==b)
        continue;
        else
        {
            w=a[i]-b;
            a[i+1]+=w;
            ans++;
        }
    }
    cout<<ans;
    return 0;
}
点击查看AC代码

1321:【例6.3】删数问题(Noip1994)

#include<cstring>
#include<iostream>
#include<cstdio>
using namespace std;
int st[250],p[250];
int main()
{   
    string s;
    int cn,on=0,hn=0,tn=1,f=0;
    cin>>s>>cn; 
    //on表示已经删除的数字个数 
    for(int i=0;i<s.size();i++)st[i]=s[i]-'0',p[i]=1;
    while(tn<s.size())
    {
        if(st[hn]>st[tn])
        {
            p[hn]=0;
            on++;
            if(on==cn)break;
            while(hn>=0&&p[hn]==0)hn--;
            if(hn<0)hn=tn,tn++;
        }
        else hn=tn,tn++;
    }
    on=0;//on表示已经输出的数字个数(前导零不输出,但要算一个输出数字) 
    for(int i=0;i<s.size();i++)
    {
        if(p[i])
        {
            if(st[i]!=0)f=1;//遇到第一个非零数字即表示可以开始输出 
            if(f)cout<<st[i];
            on++;
            if(on==s.size()-cn)break;
        }
    }
    return 0;
} 
点击查看AC代码

1322:【例6.4】拦截导弹问题(Noip1999)

#include<iostream>
#include<cstring>
#define MAXN 1000
using namespace std;
int a[MAXN+10];//导弹飞来时的高度 
int l[MAXN+10];//拦截导弹最低高度 
int main()
{    
    memset(a,0,sizeof(a));    
    memset(l,0,sizeof(l));    
    int n=1;    
    while(cin>>a[n])    
    {        n++;    }    
    int k=1;//拦截导弹系统数    
    int p,j=1;    
    l[k]=a[1];     
    for(int i=2;i<=n;i++)     
    {        p=0;//注意每次循环时需要p=0         
         for(int j=1;j<=k;j++)//注意,j<=k     
             {            if(l[j]>=a[i])        
                 {                if(p==0) p=j;            
                         else if(l[p]>l[j]) p=j;//如果同时满足例如l[1]=155>65,l[2]=158>65,则应该应将最小值赋值给最小拦截系统     
                }        
                }    
                    if(p==0)    
                        {            k++;//如果发现a[i]>l[j],则应该增加一个系统         
                            l[k]=a[i];//更新新系统的最小值     
                        }    
                        else l[p]=a[i];//更新原系统的拦截最小值     
                        }    
                        cout<<k<<endl;
                            return 0; 
        }
点击查看AC代码

1323:【例6.5】活动选择

#include<bits/stdc++.h>
using namespace std;
struct huodong
{
    int b;
    int e;
    int num;
} a[1010];
int main()
{
    int n;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>a[i].b>>a[i].e;
        a[i].num=i;
    }
    for(int i=1;i<=n-1;i++)
         for(int j=1;j<=n-i;j++)
         {
             if(a[j].e>a[j+1].e)
               swap(a[j],a[j+1]);
         }
    int min=a[1].e;
    int coutt=1;
    for(int i=2;i<=n;i++)
    {
        if(a[i].b>=min)
        {
            coutt++;
            min=a[i].e;
        }
    }
    cout<<coutt<<endl;
    return 0;
}
点击查看AC代码

1324:【例6.6】整数区间

#include<iostream>
#include<algorithm>
using namespace std;
struct qj{
    int l,r;
}a[10001]; 
bool  cmp(qj x,qj y)
{
    return x.r<y.r;
}
int main()
{
    int n;
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i].l>>a[i].r;
    sort(a+1,a+n+1,cmp);
    int x=-1,ans=0;
    for(int i=1;i<=n;i++)
    {
        if(a[i].l>x)
        {
            x=a[i].r;
            ans++;
        }
    }
    cout<<ans;
    return 0;
}
点击查看AC代码

1223:An Easy Problem

#include<iostream>
using namespace std;
int a[100],b[10000],n,nn;
int t(int x)
{
    int xn=0;
    while(x)
    {
        if(x%2)xn++;
        x/=2;
    }
    return xn;
 } 
int main(){
    int x;
    while(cin>>x&&x)
    {
        n=t(x);
        int tmp=x+1;
        while(t(tmp)!=n)tmp++;
        b[nn++]=tmp;
     } 
     for(int i=0;i<nn;i++)cout<<b[i]<<endl;
    return 0;
}
点击查看AC代码

1224:最大子矩阵

#include <iostream>  
#include <cstring>  
using namespace std;  
const int maxn =101;
int n,m,res=-127;  
int a[maxn][maxn],b[maxn],dp[maxn];  
int main()  
{  
    cin>>n;
    m=n;  
    for(int i=0;i<n;i++)  
       for(int j=0;j<m;j++)  
          cin>>a[i][j];  
    for(int x=0;x<n;x++){//设置起始行   
        memset(b,0,sizeof(b));//设置结束行   
        for(int y=x;y<n;y++)
        {  
            for(int j=0;j<m;j++)  
                b[j]+=a[y][j];//b存储第起始行x到y行到中每一列的值   
            dp[0]=b[0];
            if(dp[0]>res)//不要忘了这个   
                res=dp[0]; 
            for(int i=1;i<m;i++)
            {  
                if(dp[i-1]<0)  
                    dp[i]=b[i];  
                else   
                   dp[i]=dp[i-1]+b[i];  
                if(dp[i]>res)          //维护最后的结果   
                   res=dp[i];  
            }  

        }  
    }  
    cout<<res<<endl;  
    return 0;  
} 
点击查看AC代码

1225:金银岛

//1225:金银岛
#include<iostream>
#include<algorithm>
#include<iomanip>
using namespace std;
struct bb{
    int t,v;
    double bl;
    void bin()
    {
        cin>>t>>v;
        bl=1.0*v/t;
    }
}a[10001];
bool cmp(bb x,bb y)
{
    return x.bl>y.bl;
}
int main()
{
    int t,w,n;
    double ans;
    cin>>t;
    for(int i=1;i<=t;i++)
    {
        ans=0;
        cin>>w>>n;
        for(int j=1;j<=n;j++)a[j].bin();
        sort(a+1,a+n+1,cmp);
        for(int j=1;j<=n&&w>0;j++)
        {
            if(a[j].t<=w)
            {
                w-=a[j].t;
                ans+=a[j].v;
            }
            else
            {
                ans+=a[j].bl*w;
                w=0;
            }
        }
        cout<<fixed<<setprecision(2)<<ans<<endl;
    }
    return 0;
}
点击查看AC代码

1226:装箱问题

#include<bits/stdc++.h>
using namespace std;
int main()
{
    int n,a,b,c,d,e,f,x,y;
    int u[4]={0,5,3,1};
    while(1){
        scanf("%d%d%d%d%d%d",&a,&b,&c,&d,&e,&f);
        if(a==0&&b==0&&c==0&&d==0&&e==0&&f==0)
            break;
        n=d+e+f+(c+3)/4;
        y=5*d+u[c%4];
        if(b>y)
            n+=(b-y+8)/9;
        x=36*n-36*f-25*e-16*d-9*c-4*b;
        if(a>x)
            n+=(a-x+35)/36;
          cout<<n<<endl;
        
    }
  
    return 0;
}
点击查看AC代码

1227:Ride to Office

//1227:Ride to Office 
//这个题没给速度和时间单位,根据样例数据只能理解为时间为秒,速度单位为公里/小时 
#include<iostream>
#include<cmath>
using namespace std;
int const N=1e4+2;
int n,ans,t,v; 
int main(){
    while(cin>>n&&n)
    {
        ans=1e5;
        for(int i=1;i<=n;i++)
        {
            cin>>v>>t;
            if(t>=0&&16200.0/v+t<ans)ans=ceil(16200.0/v+t);
        }
        cout<<ans<<endl;
    }
    return 0;
}
点击查看AC代码

1228:书架

//1228:书架
#include<iostream>
#include<algorithm>
using namespace std;
typedef long long ll;
int hi[20001],sum[20001];
bool cmp(ll x,ll y)
{
    return x>y;
}
int main()
{
    int n,b;
    cin>>n>>b;
    for(int i=1;i<=n;i++)cin>>hi[i];
    sort(hi+1,hi+n+1,cmp);
    for(int i=1;i<=n;i++)sum[i]=sum[i-1]+hi[i];
    int l=1,r=n;
    while(l<r)
    {
        int m=(l+r)>>1;
        if(sum[m]>=b)r=m;
        else l=m+1;
        
     } 
     cout<<r;
    return 0;
}
点击查看AC代码

1229:电池的寿命

//1229:电池的寿命
#include<iostream>
#include<iomanip>
using namespace std;
int n, a[1001]; 
int main(){
    int mx,mn,sm;
    while(cin>>n)
    {
        mx=sm=0;
        mn=1e8; 
        for(int i=0;i<n;i++)
        {
            cin>>a[i];
            if(a[i]>mx)mx=a[i];
            if(a[i]<mn)mn=a[i];
            sm+=a[i];
        }
        if(2==n)cout<<fixed<<setprecision(1)<<mn*1.0<<endl;
        else if(sm<mx*2)cout<<fixed<<setprecision(1)<<1.0*sm-mx<<endl;
        else cout<<fixed<<setprecision(1)<<sm/2.0<<endl;
    }
    return 0;
}
点击查看AC代码

1230:寻找平面上的极大点

//1230:寻找平面上的极大点
#include<iostream>
using namespace std;
int a[101];//存以x为坐标的所有点的最大纵坐标,对应点(x,a[x])即为极 
int main(){
    int n,x,y,f=0,mx=0;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>x>>y;
        if(a[x]<y)a[x]=y;
    }
     for(int i=100;i>=0;i--)
     {
         if(a[i]>mx)mx=a[i];
         else a[i]=0;
     }
    for(int i=0;i<=100;i++)
    {
        if(!a[i])continue;
        if(f)cout<<',';
        cout<<'('<<i<<','<<a[i]<<')';
        f=1;
    }
    return 0;
}
点击查看AC代码

1231:最小新整数

//1231:最小新整数
int a[10],p[10]; 
#include<iostream>
#include<cstring>
using namespace std;
int main(){

    int n,num,k,len;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        memset(p,0,sizeof(p));
        len=0;
        cin>>num>>k;
        while(num)
        {
            a[++len]=num%10;
            num/=10;
        }
        int l=len,r=len-1,sl=0;
        while(sl<k&&r>=1)
        {
            if(a[l]>a[r])
            {
                p[l]=1;
                sl++;
                while(p[l])l++;
            }
            else l=r,r--;
            if(l==len+1)l=r,r--;
        }
        sl=0;
        for(int j=len;j>=1&&sl<len-k;j--)
        {
            while(p[j])j--;
            cout<<a[j];
            sl++;
        }
        cout<<endl;
    }
    return 0;
}
点击查看AC代码

1232:Crossing River

//1232:Crossing River
#include<iostream>
#include<algorithm>
using namespace std;
int const N=1e5+2;
int a[N],n,m,ans; 
int main(){
    cin>>m;
    while(m--)
    {
        cin>>n;
        for(int i=1;i<=n;i++)cin>>a[i];
        sort(a+1,a+n+1);
        ans=0;
        while(n>3)
        {            
            if(a[n]+a[2]*2+a[1]<a[n]+a[n-1]+a[1]*2)ans+=a[n]+a[2]*2+a[1];
            else ans+=a[n]+a[n-1]+a[1]*2;
            n-=2;
        }
        if(n==3)ans+=a[3]+a[1]+a[2];
        if(n==2)ans+=a[2];
        if(n==1)ans=a[1];    
        cout<<ans<<endl;
    }
    return 0;
}
点击查看AC代码

1233:接水问题

//1233:接水问题
#include<iostream>
using namespace std;
int ans,n,m,a[1000001];
long long b[1000001];
int main(){
    cin>>n>>m;
    for(int i=1;i<=n;i++)cin>>a[i];
    for(int i=1;i<=m;i++)
        if(i<=n)b[i]=a[i];
        else b[i]=0;
    for(int i=m+1;i<=n;i++)
    {
        int k=1,minx=b[1];
        for(int j=2;j<=m;j++) 
            if(b[j]<minx)minx=b[j],k=j;
        b[k]+=a[i];
    }
    ans=b[1];
    for(int i=2;i<=m;i++)
        if(ans<b[i])ans=b[i];
    cout<<ans<<endl;
    return 0;
}
点击查看AC代码

第七章 分治算法

1325:【例7.4】 循环比赛日程表

#include<iostream>
using namespace std;
int sc[130][130],n;
void makelist(int fx,int fy,int lx,int ly,int fn,int ln){
    if(fn==ln)sc[fx][fy]=fn;
    else {
        int tmpx=(fx+lx)/2,tmpy=(fy+ly)/2,tmpn=(fn+ln)/2;
        makelist(fx,fy,tmpx,tmpy,fn,tmpn);
        makelist(fx,tmpy+1,tmpx,ly,tmpn+1,ln);
        makelist(tmpx+1,fy,lx,tmpy,tmpn+1,ln);
        makelist(tmpx+1,tmpy+1,lx,ly,fn,tmpn);
    }
} 
void printlist(int n){
    for(int i=1;i<=n;i++){
        for(int j=1;j<=n;j++)cout<<sc[i][j]<<' ';
        cout<<endl;
    }
}
int main(){
    cin>>n;
    n=1<<n;
    makelist(1,1,n,n,1,n);
    printlist(n); 
    return 0;
}
点击查看AC代码

1326:【例7.5】 取余运算(mod)

#include<iostream>
using namespace std;
long b,p,k;
long mmod(long b,long p,long k)
{
    if(p==1)return b%k;
    long long t=mmod(b,p/2,k);
    t=t*t%k;
    if(p%2)t=t*b%k;
    return long(t); 
 } 
int main(){
    cin>>b>>p>>k;
    cout<<b<<'^'<<p<<" mod "<<k<<'='<<mmod(b,p,k);
    return 0;
}
点击查看AC代码

1327:【例7.6】黑白棋子的移动

#include<cstdio>
char ch[10000];
int n,h;
void pr()
{
    printf("step%2d:",h++);
    for(int i=0;i<=2*n+1;i++)
    printf("%c",ch[i]);
    printf("\n");
    return;
}
void move(int x,int y)
{
    ch[y]=ch[x],ch[y+1]=ch[x+1];
    ch[x]=ch[x+1]='-';
    return;
 } 
int main(){
    scanf("%d",&n);
    for(int i=0;i<n;i++)ch[i]='o'; 
    for(int i=n;i<2*n;i++)ch[i]='*';
    ch[2*n]=ch[2*n+1]='-';
    pr();
    for(int i=0;i<n-4;i++)
    {
        move(n-1-i,2*(n-i));
        pr();
        move(2*(n-i-1),n-1-i);
         pr();
     } 
     move(3,8);
     pr();
     move(7,3);
     pr();
     move(1,7);
     pr();
     move(6,1);
     pr();
     move(0,6);
     pr();
    return 0;
}
点击查看AC代码

1328:【例7.7】光荣的梦想

//1328:【例7.7】光荣的梦想 
#include<iostream>
using namespace std;
int n,a[10001],ans;
int main(){
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i];
    for(int i=1;i<n;i++)
        for(int j=1;j<=n-i;j++)
        {
            if(a[j]>a[j+1])
            {
                int t=a[j+1];
                a[j+1]=a[j];
                a[j]=t;
                ans++;
            }
        }
    cout<<ans<<endl;
    //for(int i=1;i<=n;i++)cout<<a[i]<<' ';
    return 0;
}
点击查看AC代码

1234:2011

#include<iostream>
using namespace std;
int a[200][10],b[200][200],mx;
int js(int base,int n)
{
    if(n==1)return base;
    if(n%2)return js(base,n-1)*base%10000;
    else return js(base,n/2)*js(base,n/2)%10000;
}
void ini()
{    
    a[0][1]=2011,a[0][0]=1;
    for(int i=2;i<10;i++)a[0][i]=a[0][i-1]*2011%10000;
    for(int i=1;i<mx;i++)
        for(int j=0;j<10;j++)
        {
            if(j==0)a[i][j]=1;
            else if(j==1)a[i][j]=a[i-1][9]*a[i-1][1]%10000;
            else a[i][j]=a[i][j-1]*a[i][1]%10000;
        }
}
int js2(int x,int n)
{
    int i=0,ans=1;
    while(i<n)
    {
        ans*=a[i][b[x][i+1]];
        ans%=10000;
        i++;
    }
    return ans;
}
int main(){
    int n,l;
    string s;
    cin>>n;
    for(int i=0;i<n;i++)
    {
        cin>>s;
        l=s.size();
        if(l>mx)mx=l;
        b[i][0]=l;
        for(int j=1;j<=l;j++)
            b[i][j]=s[l-j]-'0';
    }
    ini();
    for(int i=0;i<n;i++)cout<<js2(i,b[i][0])<<endl;
    return 0;
}
点击查看AC代码

1235:输出前k大的数

//1235:输出前k大的数
#include<cstdio>
int const N=1e5+1;
int a[N],n,k;
void qs(int low,int high)
{
    int l=low,h=high;
    int key=a[l];
    while(l<h)
    {
        while(l<h&&a[h]>=key)h--;
        a[l]=a[h];
        while(l<h&&a[l]<=key)l++;
        a[h]=a[l];
     } 
     a[l]=key;
     if(l>n-k+1&&low<l-1)qs(low,l-1);
     if(high>l+1)qs(l+1,high);
}
int main(){
    scanf("%d",&n);
    for(int i=1;i<=n;i++)scanf("%d",a+i);
    scanf("%d",&k);
    qs(1,n);
    while(k--)printf("%d\n",a[n--]);
    return 0;
}
点击查看AC代码

1236:区间合并

//1236:区间合并 
#include<iostream>
#include<algorithm>//排序函数调用 
using namespace std;
int const N=5e4+1;
struct qj{
    int l,r;
    bool operator < (qj const x){
        if(l<x.l||l==x.l&&r<x.r)return true;
        else return false;
    } 
}a[N];
int n,x,y; 
int main(){
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i].l>>a[i].r;
    sort(a+1,a+n+1);
    x=a[1].l,y=a[1].r;
    for(int i=2;i<=n;i++)
        if(a[i].l>y)
        {
            cout<<"no";
            return 0;
        }
        else if(a[i].r>y)y=a[i].r;
    cout<<x<<' '<<y<<endl;
    return 0;
}
点击查看AC代码

1237:求排列的逆序数

//1237:求排列的逆序数
#include<iostream>
using namespace std;
int const N=1e5+1;
int a[N],b[N],n;
long long ans;
void gb(int low,int high)
{
    if(low>=high)return;
    int l=low,r=high,m=(low+high)/2;
    gb(l,m);
    gb(m+1,r);
    int i=l,j=m+1,k=l;
    while(i<=m&&j<=r)
        if(a[i]<=a[j])b[k++]=a[i++];
        else    b[k++]=a[j++],ans+=m-i+1;
    while(i<=m)b[k++]=a[i++];
    while(j<=r)b[k++]=a[j++];
    for(i=l;i<=r;i++)a[i]=b[i];
}
int main(){
    ios::sync_with_stdio(false);
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i];
    gb(1,n);
    //for(int i=1;i<=n;i++)cout<<a[i]<<' ';
    cout<<ans<<endl;
    return 0;
}
点击查看AC代码

1238:一元三次方程求解

//1238:一元三次方程求解
#include<iostream>
#include<iomanip> 
using namespace std;
int k;
double ans[3],a,b,c,d,x0=-101;
int f(double x)
{
    double y;
    y=a*x+b;
    y=x*y+c;
    y=x*y+d;
    if(-y>1e-12)return -1;
    else if(y>1e-12)return 1;
    else return 0;
}
double f1(double x)
{
    double y;
    y=a*x+b;
    y=x*y+c;
    y=x*y+d;
    return y;
}
double key(double x,double y)
{
    //cout<<'['<<x<<','<<y<<']';
    double m=(x+y)/2;
    if(y-x<0.0005||f(m)==0)return m;
    if(f(x)*f(m)==1)return key(m,y);
    else return key(x,m);
}
int main(){
    cin>>a>>b>>c>>d;     
    for(double i=-100;i<=100;i+=0.5)
        if(f(i)==0)
        {
            ans[k++]=i;
            x0=i+0.5;
            if(k==3)break;
        }
        else if(f(x0)*f(i)==1)x0=i;
        else 
        {
            ans[k++]=key(x0,i);
            x0=i;
            if(k==3)break;
        }
    for(int i=0;i<3;i++)
    cout<<fixed<<setprecision(2)<<ans[i]<<' ';
    return 0;
}
点击查看AC代码

1239:统计数字

//1239:统计数字
#include<iostream>
using namespace std;
int const inf=2e9;
int n,a[20001],b[20001],x,cnt,p;
int pos(int x,int l,int r)
{
    int m=(l+r)/2;
    if(r-l==2)return m;
    if(m%2)m--;
    if(x==a[m])return m;
    if(x<a[m])return pos(x,l,m);
    return pos(x,m,r);
}
int main(){
    ios::sync_with_stdio(false);
    a[0]=-1,a[2]=inf;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>x;
        p=pos(x,0,cnt+2);
        if(p%2)
        {
            cnt+=2;
            for(int j=cnt+2;j>p+1;j-=2)a[j]=a[j-2],b[j]=b[j-2];
            a[p+1]=x,b[p+1]=1;
        }
        else b[p]++;            
    }
    for(int i=2;i<=cnt;i+=2)cout<<a[i]<<' '<<b[i]<<endl;
    return 0;
}
点击查看AC代码

1240:查找最接近的元素

//1240:查找最接近的元素 
#include<iostream>
using namespace std;
int a[100000],n,m,q,ans[10001]; 
int main(){
    cin>>n;
    for(int i=0;i<n;i++)cin>>a[i];
    cin>>m;
    for(int i=0;i<m;i++)
    {
        cin>>q;
        if(q<=a[0])
        {
            ans[i]=a[0];
            continue;
        }
        if(q>=a[n-1])
        {
            ans[i]=a[n-1];
            continue;
        }
        int l=0,r=n-1,mid;
        while(l<r-1)
        {
            mid=(l+r)>>1;
            if(a[mid]==q)
            {
                ans[i]=mid;
                l=r=mid;
            }
            else if(a[mid]>q)r=mid;
            else l=mid;
        }
        if(a[l]+a[r]>=q*2)ans[i]=a[l];
        else ans[i]=a[r];
    }
    for(int i=0;i<m;i++)cout<<ans[i]<<endl;
    return 0;
}
点击查看AC代码

1241:二分法求函数的零点

//1241:二分法求函数的零点
#include<iostream>
#include<iomanip>
using namespace std;
double a[6]={1},b[6]={-121,274,-225,85,-15,1};
void fc(double x)
{
    for(int i=1;i<=5;i++)
    a[i]=a[i-1]*x;
    return;
}
double f(double x)
{
    double t=0;
    fc(x);
    for(int i=0;i<6;i++)t+=a[i]*b[i];
    if(t>1e-12)return 1;
    else if(t<-1e-12)return -1;
    return 0;
}
int main()
{
    double l=1.5,r=2.4,mid;
    while(r-l>1e-8)
    {
        mid=(l+r)/2;
        //cout<<l<<' '<<r<<' '<<f(mid)<<' '<<mid<<endl;
        if(f(mid)==1)l=mid;
        else if(f(mid)==-1)r=mid;
        else break;
     } 
     cout<<fixed<<setprecision(6)<<mid;
    return 0;
}
点击查看AC代码

1242:网线主管

//1242:网线主管 
#include<iostream>
#include<iomanip>
using namespace std;
int const N=1e4+1;
long long  b[N],ans,n,s;
double t;
long long  ts(int x)
{
    long long int num=0;
    for(int i=1;i<=n;i++)num+=b[i]/x;
    return num;
}
int f(int l,int r)
{
    int m=(l+r)/2;
    if(r-l<=1)return l;
    if(ts(m)>=s)return f(m,r);
    else return f(l,m);
}
int main(){
    cin>>n>>s;
    for(int i=1;i<=n;i++)
    {
        cin>>t;
        b[i]=t*100+0.1;
    }
    if(ts(1)<s)ans=0;
    else if(ts(1e8)>=s)ans=1e8;
    else ans=f(1,1e8);
    cout<<fixed<<setprecision(2)<<ans/100.0+0.0001;
    return 0;
}
点击查看AC代码

1243:月度开销

//1243:月度开销 
#include<iostream>
using namespace std;
int const N=1e5+1;
int a[N],s[N],n,m,max1,maxn; 
bool tj(int x)
{
    int cnt=1,ts=0;
    for(int i=1;i<=n;i++)
        if(ts+a[i]<=x)ts+=a[i];
        else ts=a[i],cnt++;
    return cnt<=m;
}
int main(){
    cin>>n>>m;
    for(int i=1;i<=n;i++)
    {
        cin>>a[i];
        s[i]=s[i-1]+a[i];
        if(max1<a[i])max1=a[i];
    }
    maxn=s[n-m];
    for(int i=n-m+1;i<=n;i++)
        if(maxn<s[i]-s[i-n+m])maxn=s[i]-s[i-n+m];
    int l=max1-1,r=2e9;
    while(l+1<r)
    {
        int mm=(l+r)/2;
        if(tj(mm))r=mm;
        else l=mm;
    }
    cout<<r;
    return 0;
}
点击查看AC代码

1244:和为给定数

//1244:和为给定数 
#include<iostream>
#include<algorithm>
using namespace std;
int const N=1e5+1;
int a[N],n,m; 
int main(){
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i];
    cin>>m;
    sort(a+1,a+n+1);
    int i=1,j=n;
    while(i<j)
    {
        if(a[i]+a[j]==m)break;
        else if(a[i]+a[j]<m)i++;
        else j--;
    }
    if(i<j)cout<<a[i]<<' '<<a[j];
    else cout<<"No";
    return 0;
}
点击查看AC代码

1245:不重复地输出数

//1245:不重复地输出数
#include<iostream>
#include<algorithm>
using namespace std;
int const N=1e5+1;
int a[N],n;
int main(){
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i];
    sort(a+1,a+1+n);
    int x=a[1];
    cout<<x;
    for(int i=2;i<=n;i++)
        if(a[i]!=x)
        {
            cout<<' '<<a[i];
            x=a[i];
        }
    return 0;
}
点击查看AC代码

1246:膨胀的木棍

//1246:膨胀的木棍
#include<iostream>
#include<iomanip>
#include<cmath>
using namespace std;
int main(){
    double l,d,c,n,r,alf,x;
    cin>>d>>n>>c;
    l=d*(1+n*c);
    //解方程lsing(alf) =alf*d
    double m=0;n=acos(-1.0)/2;
    while(n-m>1e-12)
    {
        double b=(m+n)/2;
        if(l*sin(b)>b*d)m=b;
        else if(l*sin(b)<b*d)n=b;
    }
    alf=m;
    r=l/alf/2;
    x=r-r*cos(alf);
    cout<<fixed<<setprecision(3)<<x;
    return 0;
}
点击查看AC代码

1247:河中跳房子

//1247:河中跳房子 
#include<iostream>
using namespace std;
int const N=5e4+2;
int s[N],a[N],l,n,m; 
bool ts(int x)
{
    int jl=0,cnt=0;
    for(int i=1;i<=n;i++)
        if(l-s[i]<x)cnt+=n+1-i,i=n+1;
        else if(jl+a[i]<x)cnt++,jl+=a[i];
        else jl=0;
    return cnt<=m;
}
int main(){
    cin>>l>>n>>m;
    for(int i=1;i<=n;i++)
    {
        cin>>s[i];
        a[i]=s[i]-s[i-1];
    }
    int low=1,high=l;
    while(low+1<high)
    {
        int mid=(low+high)/2;
        if(ts(mid))low=mid;
        else high=mid;
    }
    cout<<low;
    return 0;
}
点击查看AC代码

第八章 广度优先搜索算

1329:【例8.2】细胞

#include<iostream>
using namespace std;
int n,m,ans,tmp,a[110][110],que[110*110][2];
int fx[4][2]={{-1,0},{1,0},{0,-1},{0,1}};
void bfs(int x,int y){
    int head=0,tail=1,curx,cury;
    que[0][0]=x,que[0][1]=y;
    while(head<tail){
        curx=que[head][0];
        cury=que[head++][1];
        for(int i=0;i<4;i++){
            int tmpx=curx+fx[i][0];
            int tmpy=cury+fx[i][1];
            if(a[tmpx][tmpy]) {
                que[tail][0]=tmpx;
                que[tail++][1]=tmpy;
                a[tmpx][tmpy]=0;
            }
        } 
    }
}
int main(){
    //freopen("blacks.in","r",stdin);
    cin>>n>>m;
    char ch;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)
        {
            cin>>ch;
            if(ch>'0')a[i][j]=1;
        }
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)
            if(a[i][j]){
                ++ans;
                bfs(i,j);
            }
    cout<<ans<<endl; 
    return 0;
}
点击查看AC代码

1330:【例8.3】最少步数

#include<iostream>
using namespace std;
int a[104][104],num[104][104],que[10000][2],ha,la,hb,lb,ans1,ans2;
int dx[12]={2,2,2,2,1,1,-1,-1,-2,-2,-2,-2};
int dy[12]={2,1,-1,-2,2,-2,2,-2,2,1,-1,-2};
void bfs()
{
    int h=0,t=1,cx,cy,tx,ty;
    que[0][0]=1,que[0][1]=1;
    num[1][1]=0,a[1][1]=1;
    while(h<t)
    {
        cx=que[h][0],cy=que[h][1];
        for(int i=0;i<12;i++)
        {
            tx=cx+dx[i],ty=cy+dy[i];
            if(tx>=1&&tx<=100&&ty>=1&&ty<=100&&a[tx][ty]==0)
            
                {
                    que[t][0]=tx,que[t][1]=ty;
                    t++;
                    num[tx][ty]=num[cx][cy]+1;
                    a[tx][ty]=1;
                    if(tx==ha&&ty==la)ans1=num[tx][ty];
                    if(tx==hb&&ty==lb)ans2=num[tx][ty];
                    if(ans1&&ans2)return;
                 } 
         }
         h++;
    }
}
int main(){
    cin>>ha>>la>>hb>>lb;
    bfs();
    cout<<ans1<<endl<<ans2;
    return 0;
}
点击查看AC代码

1248:Dungeon Master

#include<iostream>
#include<cstring>
using namespace std;
const int mxn=25;
int n,x,y,z,sx,sy,sz,ex,ey,ez,ans[100];
int map[mxn][mxn][mxn],flag[mxn][mxn][mxn],que[mxn*mxn*mxn][3];
int dx[6]={1,-1,0,0,0,0};
int dy[6]={0,0,1,-1,0,0};
int dz[6]={0,0,0,0,1,-1};
void bfs()
{
    int h=0,t=0,cx,cy,cz,tx,ty,tz;
    que[0][0]=sx,que[0][1]=sy,que[0][2]=sz;
    while(h<=t)
    {
        cx=que[h][0],cy=que[h][1],cz=que[h][2];
        for(int i=0;i<6;i++)
        {
            tx=cx+dx[i],ty=cy+dy[i],tz=cz+dz[i];
            if(tx==ex&&ty==ey&&tz==ez)
            {
                ans[n]=map[cx][cy][cz]+1;
                return;
            }
            if(flag[tx][ty][tz])
            {
                map[tx][ty][tz]=map[cx][cy][cz]+1;
                ++t;
                que[t][0]=tx,que[t][1]=ty,que[t][2]=tz;
                flag[tx][ty][tz]=0;
            }
        }
        h++;
    }
}
int main(){
    char ch;
    while(1)
    {
        cin>>z>>x>>y;
        if(!(x||y||z))break; 
        n++;
        memset(map,0,sizeof(map));
        memset(flag,0,sizeof(flag));
        for(int k=1;k<=z;k++)
            for(int i=1;i<=x;i++)
                for(int j=1;j<=y;j++)
                {
                    cin>>ch;
                    if(ch=='.')flag[i][j][k]=1;
                    if(ch=='S')sx=i,sy=j,sz=k;
                    if(ch=='E')ex=i,ey=j,ez=k;
                }
        bfs();
    }
    for(int i=1;i<=n;i++)
        if(ans[i])cout<<"Escaped in "<<ans[i]<<" minute(s).\n";
        else cout<<"Trapped!\n";
    return 0;
}
点击查看AC代码

1249:Lake Counting

#include<iostream>
using namespace std;
const int mxn=114;
int n,m,map[mxn][mxn],que[mxn*mxn][2],ans;
int dx[]={1,-1,0,0,1,1,-1,-1};
int dy[]={0,0,1,-1,1,-1,1,-1};
void bfs(int x,int y)
{
    int h=0,t=0,cx,cy,tx,ty;
    que[0][0]=x,que[0][1]=y;
    map[x][y]=0;
    while(h<=t)
    {
        cx=que[h][0],cy=que[h][1];
        for(int i=0;i<8;i++)
        {
            tx=cx+dx[i],ty=cy+dy[i];
            if(map[tx][ty])
            {
                que[++t][0]=tx,que[t][1]=ty;
                map[tx][ty]=0;
            }
        }
        ++h;
    }
}
void dfs(int x,int y)
{
    map[x][y]=0;
    int tx,ty;
    for(int i=0;i<8;i++)
    {
        tx=x+dx[i],ty=y+dy[i];
        if(map[tx][ty])dfs(tx,ty);
    }
}
int main(){
    int n,m;
    char ch;
    cin>>n>>m;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)
        {
            cin>>ch;
            if(ch=='W')map[i][j]=1;
        }    
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)
        {
            if(map[i][j])
            {
                ans++;
                bfs(i,j);//也可dfs(i,j); 
            }
        }
    cout<<ans;        
    return 0;
}
点击查看AC代码

1250:The Castle

#include<bits/stdc++.h>
using namespace std;
int a[52][52],p[52][52],mx,ans,fj;
int dx[4]={0,-1,0,1};
int dy[4]={-1,0,1,0};
void dfs(int x,int y);
int main(){
    std::ios::sync_with_stdio(false);
    int r,c;
    cin>>r>>c;
    for(int i=1;i<=r;i++)
        for(int j=1;j<=c;j++)
            cin>>a[i][j];
    for(int i=1;i<=r;i++)
        for(int j=1;j<=c;j++)
        {
            if(p[i][j]==0)
            {
                fj++;
                ans=0;
                dfs(i,j);
                if(mx<ans)mx=ans;
            }
        }
    cout<<fj<<endl<<mx;
    return 0;
}
void dfs(int x,int y)
{
    ans++;
    p[x][y]=1;
    int tx,ty;
    for(int i=0;i<4;i++)
    {
        if((a[x][y]>>i)%2==0)
        {
            tx=x+dx[i],ty=y+dy[i];
            if(p[tx][ty]==0)dfs(tx,ty);    
        }
    }
}
点击查看AC代码

1251:仙岛求药

#include<iostream>
#include<cstring>
using namespace std;
int const mx=22;
int a[mx][mx],m[mx*mx][mx*mx],que[mx*mx][mx*mx],ans[1000];
int ha,la,hb,lb,r,c,h,t; 
//m记录搜索路径 
int dx[4]={1,0,-1,0};
int dy[4]={0,1,0,-1};
int bfs(int x,int y) ;
int main(){
    char ch;
    int tmp=0; 
    while(1)
    {
        cin>>r>>c;
        if(r==0&&c==0)break;
        memset(a,0,sizeof(a));
        memset(m,0,sizeof(m));
        for(int i=1;i<=r;i++)
            for(int j=1;j<=c;j++)
            {
                cin>>ch;
                if(ch=='.')a[i][j]=1;
                if(ch=='@')ha=i,la=j;
                if(ch=='*')hb=i,lb=j;
            }
        m[ha][la]=0; 
        ans[tmp++]=bfs(ha,la);    
    } 
    for(int i=0;i<tmp;i++)cout<<ans[i]<<endl;
    return 0;
}
int bfs(int x,int y)
{
    que[0][0]=x,que[0][1]=y;
    int cx,tx,cy,ty;
    h=0,t=0;
    while(h<=t)
    {
        cx=que[h][0],cy=que[h++][1];
        for(int i=0;i<=3;i++)
        {
            tx=cx+dx[i],ty=cy+dy[i];
            if(tx==hb&&ty==lb)
                return m[cx][cy]+1;
            if(a[tx][ty])
            {
                que[++t][0]=tx,que[t][1]=ty;
                a[tx][ty]=0;
                m[tx][ty]=m[cx][cy]+1;
            }
        }
    }
    return -1;
}
点击查看AC代码

1252:走迷宫

#include<iostream>
using namespace std;
int a[100][100],m[100][100],n,k,f,que[10000][10000],h,t;
//m记录搜索路径 
int dx[4]={1,0,-1,0};
int dy[4]={0,1,0,-1};
void bfs(int x,int y) ;
int main(){
    char ch;
    cin>>n>>k;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=k;j++)
        {
            cin>>ch;
            if(ch=='.')a[i][j]=1;
        }
    m[1][1]=1; 
    bfs(1,1);
    return 0;
}
void bfs(int x,int y)
{
    que[0][0]=x,que[0][1]=y;
    int cx,tx,cy,ty;
    while(h<=t)
    {
        cx=que[h][0],cy=que[h++][1];
        for(int i=0;i<=3;i++)
        {
            tx=cx+dx[i],ty=cy+dy[i];
            if(tx==n&&ty==k)
            {
                cout<<m[cx][cy]+1;
                return;
            }
            if(a[tx][ty])
            {
                que[++t][0]=tx,que[t][1]=ty;
                a[tx][ty]=0;
                m[tx][ty]=m[cx][cy]+1;
            }
        }
    }
}
点击查看AC代码

1253:抓住那头牛

#include<iostream>
using namespace std;
int m[10000000],n,k,f,que[10000000],h,t,p[10000000];
//m记录搜索路径 
int zn(int x,int i);
void bfs(int x) ;
int main(){
    cin>>n>>k;
    m[n]=0; 
    bfs(n);
    return 0;
}
int zn(int x,int i)
{
    if(i==1)return x-1;
    if(i==2)return x+1;
    return x*2;
}
void bfs(int x)
{
    que[0]=x;
    int cx,tx;
    while(h<=t)
    {
        cx=que[h++];
        for(int i=1;i<=3;i++)
        {
            tx=zn(cx,i);
            if(p[tx]==0&&tx<k+100000&&tx>=0)
            {
                if(tx==k)
                {
                    cout<<m[cx]+1;
                    return;
                }
                que[++t]=tx;
                p[tx]=1;
                m[tx]=m[cx]+1;
            }
        }
    }
}
点击查看AC代码

1254:走出迷宫

#include<bits/stdc++.h>
using namespace std;
int const mx=102;
int dx[4]={0,1,0,-1};
int dy[4]={1,0,-1,0};
int a[mx][mx],que[mx*mx][2],ans,dp[mx][mx],ha,la,hb,lb;
void bfs()
{
    int h=0,t=0,cx,cy,tx,ty;
    que[0][0]=ha,que[0][1]=la;
    while(h<=t)
    {
        cx=que[h][0],cy=que[h++][1];
        for(int i=0;i<4;i++)
        {
            tx=cx+dx[i];
            ty=cy+dy[i];
            if(tx==hb&&ty==lb)
            {
                ans=dp[cx][cy]+1;
                return ;
            }
            if(a[tx][ty])
            {
                que[++t][0]=tx;
                que[t][1]=ty;
                dp[tx][ty]=dp[cx][cy]+1;
                a[tx][ty]=0;
            }
        }
    }
}
int main(){
    int n,m;
    string ch;
    cin>>n>>m;
    for(int i=1;i<=n;i++)
    {
        cin>>ch;
        for(int j=1;j<=m;j++)
        {
            if(ch[j-1]=='.')a[i][j]=1;
            if(ch[j-1]=='S')ha=i,la=j;
            if(ch[j-1]=='T')hb=i,lb=j;
        }
    }
        
    dp[ha][la]=0;
    bfs();
    cout<<ans;
    return 0;
}
点击查看AC代码

1255:迷宫问题

#include<iostream>
using namespace std;
int const mx=102;
int dx[4]={0,1,0,-1};
int dy[4]={1,0,-1,0};
int a[mx][mx],que[mx*mx][2],ans,dp[mx][mx][2],ha=1,la=1,hb=5,lb=5;
void pr(int x,int y)
{
    if(x!=ha||y!=la)pr(dp[x][y][0],dp[x][y][1]);
    cout<<'('<<x-1<<','<<' '<<y-1<<')'<<endl;
}
void bfs()
{
    int h=0,t=0,cx,cy,tx,ty;
    que[0][0]=ha,que[0][1]=la;
    while(h<=t)
    {
        cx=que[h][0],cy=que[h++][1];
        for(int i=0;i<4;i++)
        {
            tx=cx+dx[i];
            ty=cy+dy[i];
            if(tx==hb&&ty==lb)
            {
                pr(cx,cy);
                cout<<'('<<hb-1<<','<<' '<<lb-1<<')'; 
                return ;
            }
            if(a[tx][ty])
            {
                que[++t][0]=tx;
                que[t][1]=ty;
                dp[tx][ty][0]=cx;
                dp[tx][ty][1]=cy;
                a[tx][ty]=0;
            }
        }
    }
}
int main(){
    //std::ios::sync_with_stdio(false);
    int n=5,m=5;
    char ch;
    //cin>>n>>m;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)
        {
            cin>>a[i][j];
            if(a[i][j])a[i][j]=0;
            else a[i][j]=1;
        }
    bfs();
    return 0;
}
点击查看AC代码

1256:献给阿尔吉侬的花束

#include<iostream>
#include<cstring>
using namespace std;
int const mx=202;
int dx[4]={0,1,0,-1};
int dy[4]={1,0,-1,0};
int map[mx][mx],que[mx*mx][2],dp[mx][mx],ans[mx],ha,la,hb,lb;
int bfs()
{
    int h=0,t=0,cx,cy,tx,ty;
    que[0][0]=ha,que[0][1]=la;
    while(h<=t)
    {
        cx=que[h][0],cy=que[h++][1];
        for(int i=0;i<4;i++)
        {
            tx=cx+dx[i];
            ty=cy+dy[i];
            if(tx==hb&&ty==lb)
            {
                return dp[cx][cy]+1;
            }
            if(map[tx][ty])
            {
                que[++t][0]=tx;
                que[t][1]=ty;
                dp[tx][ty]=dp[cx][cy]+1;
                map[tx][ty]=0;
            }
        }
    }
    return 0;
}
int main(){
    //std::ios::sync_with_stdio(false);
    int t,n,m;
    char ch;
    cin>>t;
    for(int k=1;k<=t;k++)
    {
        cin>>n>>m;
        memset(map,0,sizeof(map));
        memset(dp,0,sizeof(dp));
        for(int i=1;i<=n;i++)
            for(int j=1;j<=m;j++)
            {
                cin>>ch;
                if(ch=='.')map[i][j]=1;
                if(ch=='S')ha=i,la=j;
                if(ch=='E')hb=i,lb=j; 
            }
        ans[k]=    bfs();
    }
    for(int k=1;k<=t;k++)
    {
        if(ans[k])cout<<ans[k]<<endl;
        else cout<<"oop!"<<endl; 
    }
    return 0;
}
点击查看AC代码

1257:Knight Moves

#include<iostream>
#include<cstring>
using namespace std;
int const mx=304;
int dx[8]={2,2,1,1,-1,-1,-2,-2};
int dy[8]={-1,1,-2,2,-2,2,-1,1};
int map[mx][mx],que[mx*mx][2],dp[mx][mx],ans[mx],ha,la,hb,lb;
int bfs()
{
    int h=0,t=0,cx,cy,tx,ty;
    que[0][0]=ha,que[0][1]=la;
    while(h<=t)
    {
        cx=que[h][0],cy=que[h++][1];
        for(int i=0;i<8;i++)
        {
            tx=cx+dx[i];
            ty=cy+dy[i];
            if(tx==hb&&ty==lb)
            {
                return dp[cx][cy]+1;
            }
            if(map[tx][ty])
            {
                que[++t][0]=tx;
                que[t][1]=ty;
                dp[tx][ty]=dp[cx][cy]+1;
                map[tx][ty]=0;
            }
        }
    }
    return 0;
}
int main(){
    //std::ios::sync_with_stdio(false);
    int t,n;
    char ch;
    cin>>t;
    for(int k=1;k<=t;k++)
    {
        cin>>n>>ha>>la>>hb>>lb;
        ha+=2,la+=2,hb+=2,lb+=2;
        memset(map,0,sizeof(map));
        memset(dp,0,sizeof(dp));
        for(int i=2;i<=n+1;i++)
            for(int j=2;j<=n+1;j++)
            map[i][j]=1;
        if(ha==hb&&la==lb)
        ans[k]=0;
        else ans[k]=bfs();
    }
    for(int k=1;k<=t;k++)cout<<ans[k]<<endl;
    return 0;
}
点击查看AC代码

第九章 动态规划

第一节 动态规划的基本模型

1258:【例9.2】数字金字塔

#include <bits/stdc++.h>
using namespace std;
int a[1010][1010],f[1010][1010];
int main()
{
    memset(a,0,sizeof(a));
    memset(f,0,sizeof(f));
    int R;
    cin>>R;
    for(int i=1;i<=R;i++)
        for(int j=1;j<=i;j++)
        {
            cin>>a[i][j];
        }
    for(int i=1;i<=R;i++)
    {
    for(int i=R;i>=1;i--)
        for(int j=1;j<=i;j++)
        {
            f[i][j]=a[i][j]+max(f[i+1][j],f[i+1][j+1]);
        }
    }
    cout<<f[1][1];
     return 0;
 } 
点击查看AC代码

1259:【例9.3】求最长不下降序列

//求最长不降子序列长度,一本通网站1259题 
#include<iostream>
using namespace std;
int a[201],b[201],c[201],mx=1,mxn;
void pr(int x)
{
    if(b[x]>1)pr(c[x]);
    cout<<a[x]<<' ';
    return;
}
int main(){
    int n;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>a[i];
        b[i]=1;
    }
    mxn=n;//如果最长不降子序列只有一个元素就输出最后一个元素 
    for(int i=2;i<=n;i++)
        for(int j=i-1;j>=1;j--)
            if(a[i]>=a[j]&&b[j]>=b[i])
            {
                b[i]=b[j]+1;
                if(mx<=b[i])mx=b[i],mxn=i;
                c[i]=j;
            }
    cout<<"max="<<mx<<endl;
    if(mx>1)pr(c[mxn]);//本可以直接pr(mxn),但最后会多一个空格 
    cout<<a[mxn];//为避免最后多一个空格,最后一个元素单独输出 
    return 0;
}
点击查看AC代码

1260:【例9.4】拦截导弹(Noip1999)

#include<iostream>
using namespace std;
int a[1005],b[1005],c[1005],sum=1,maxx,n;
int main()
{
    while(cin>>a[n])
    {
        b[n]=1;
        n++;
    }    
    c[1]=a[1];
    for(int i=0;i<n;i++)
    {
        for(int j=0;j<i;j++)
        {
            if(a[j]>=a[i]&&b[j]+1>=b[i])
                b[i]=b[j]+1;
        }
        maxx=max(maxx,b[i]); 
    }
    cout<<maxx<<endl;
//    for(int i=1;i<=n;i++)
    
    for(int i=0;i<n;i++)
    {
        int  minn=35000,flag=0,x;
        for(int j=1;j<=sum;j++)
        {
            if(a[i]<=c[j]&&minn>c[j])
            {
                minn=c[j];
                flag=1;
                x=j;
            }    
        }
        if(flag==0)c[++sum]=a[i];
        else c[x]=a[i];
    }
    cout<<sum;
    return 0;
}
点击查看AC代码

1261:【例9.5】城市交通路网

//1261:【例9.5】城市交通路网 
#include<iostream>
using namespace std;
int a[10001][10001],b[10001][2],p[10001][10001]; 
int n;
void bfs()
{
    for(int cx=1;cx<n;cx++)
    {
        for(int i=1;i<=p[cx][0];i++)
        {
            int tmp=p[cx][i];
            if(!b[tmp][0]||b[tmp][0]>b[cx][0]+a[cx][tmp])
            {
                b[tmp][0]=b[cx][0]+a[cx][tmp];
                b[tmp][1]=cx;
            }
        }
    }
}
void pr(int x)
{
    if(x==1){cout<<"1";return;}
    pr(b[x][1]);
    cout<<' '<<x;
}
int main(){
    cin>>n;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
        {
            cin>>a[i][j];
            if(a[i][j])
            {
                p[i][0]++;
                p[i][p[i][0]]=j;
            }
         } 
    bfs();
    cout<<"minlong="<<b[n][0]<<endl;
    pr(n);
    return 0;
}
点击查看AC代码

1262:【例9.6】挖地雷

//1262:【例9.6】挖地雷 
#include<iostream>
using namespace std;
int dj[201],sl[201][2],gx[201][201],ans[2],p[201][2];
//sl[x][0]记录挖到x地窖能挖到雷数,sl[x][1]记录x地窖的前驱 
void dfs(int x)
{
    int tx; 
    for(int i=1;i<=gx[x][0];i++)
    {
        tx=gx[x][i];
        if(sl[tx][0]<sl[x][0]+dj[tx])
        {
            sl[tx][0]=sl[x][0]+dj[tx];
            sl[tx][1]=x;
            dfs(tx);
        }            
    }
 } 
 void pr(int x)
 {
     if(!sl[x][1])cout<<x;
     else {
         pr(sl[x][1]);
         cout<<'-'<<x;
     }
     return;
 }
int main(){
    int n,x,y;
    cin>>n;
    for(int i=1;i<=n;i++){
        cin>>dj[i];
        sl[i][0]=dj[i];
    }
    for(int i=1;;i++)
    {
        cin>>x>>y;
        if(x==0&&y==0)break;
        p[y][0]=1;
        p[x][1]=1;
        gx[x][0]++;
        gx[x][gx[x][0]]=y;
    }
    for(int i=1;i<=n;i++)
    {
        if(!p[i][0])dfs(i);
    }
    for(int i=1;i<=n;i++)
        if(!p[i][1]&&sl[i][0]>ans[0])ans[0]=sl[i][0],ans[1]=i;
    pr(ans[1]);
    cout<<endl<<ans[0]; 
    return 0;
}
点击查看AC代码

1263:【例9.7】友好城市

#include<bits/stdc++.h>
using namespace std;
struct yhcs
{
    int csy;
    int cse;
}a[10005]; 
int b[10005],c[10005];
int main()
{
    int n,maxx,k,ans=0;
    cin>>n;
    for(int i=1;i<=n;i++)
    cin>>a[i].csy>>a[i].cse;
    for(int i=1;i<=n-1;i++)
        for(int j=1;j<=n-i;j++)
            if(a[j].csy>a[j+1].csy)
            swap(a[j],a[j+1]);
    for(int i=1;i<=10005;i++)
    b[i]=1;
    for(int i=1;i<=n;i++)
        {
            maxx=0;
            k=0;
            for(int j=1;j<=i-1;j++)
            {
                if(a[i].cse>a[j].cse&&b[j]>maxx)
                {
                    maxx=b[j];
                    b[i]=b[j]+1;
                    k=j;
                    c[i]=k;
                }
            }
        }
    for(int i=1;i<=n;i++)
    {
        if(ans<b[i])
        {
            ans=b[i];
        }
    }
    cout<<ans;
    return 0;
}
点击查看AC代码

1264:【例9.8】合唱队形

//1264:【例9.8】合唱队形 
#include<iostream>
using namespace std;
int n,sh,maxn,maxx,a[101],b[101][3],c[101][3];
int main(){
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i];
    maxn=1,maxx=1;
    b[1][0]=1,b[1][1]=1,b[1][2]=1;
    for(int i=2;i<=n;i++)
    {
        b[i][0]=1;
        for(int j=1;j<i;j++)
        {
            if(a[i]>a[j]&&b[i][0]<b[j][0]+1)
            {
                b[i][0]=b[j][0]+1;
                if(b[i][0]>maxn)
                    maxn=b[i][0],maxx=i;
            }
        }
        b[i][1]=maxn,b[i][2]=maxx;
     }      
    maxn=1,maxx=1;
    c[n][0]=1,c[n][1]=1,c[n][2]=1;
    for(int i=n-1;i>=1;i--)
    {
        c[i][0]=1;
        for(int j=n;j>i;j--)
        {
            if(a[i]>a[j]&&c[i][0]<c[j][0]+1)
            {
                c[i][0]=c[j][0]+1;
                if(c[i][0]>maxn)
                    maxn=c[i][0],maxx=i;
            }
        }
        c[i][1]=maxn,c[i][2]=maxx;
     }
     maxn=0;
     for(int i=2;i<n;i++)
     {
         sh=b[i][1]+c[i][1];
        if(b[i][2]==c[i][2])sh--;
        if(maxn<sh)maxn=sh; 
     }
     cout<<n-maxn;
    return 0;
}
点击查看AC代码

1265:【例9.9】最长公共子序列

//1265:【例9.9】最长公共子序列
#include<iostream>
using namespace std;
string sa,sb;
int f[1001][1001],pa,pb;
int main(){
    cin>>sa>>sb;
    int la=sa.size(),lb=sb.size();
    for(int i=1;i<=la;i++)
        for(int j=1;j<=lb;j++)
        {
            f[i][j]=max(f[i-1][j],f[i][j-1]);
            if(sa[i-1]==sb[j-1])f[i][j]=max(f[i][j],f[i-1][j-1]+1);
        }
    cout<<f[la][lb];
    return 0;
}
点击查看AC代码

1266:【例9.10】机器分配

//1266:【例9.10】机器分配
#include<iostream>
using namespace std;
int n,m,a[20][20],f[20][20],sl[20][20],maxn,maxx;
void pr(int nn,int nm)
{
    if(!nn)return;
    pr(nn-1,nm-sl[nn][nm]);
    cout<<nn<<' '<<sl[nn][nm]<<endl;
}
int main(){
    cin>>n>>m;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)cin>>a[i][j];
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)
        {
            maxn=0;
            //擂台第i个公司得到机器数量 k
            //求出最大值存于f[i][j]中 
            //第i个公司实得机器数量存在sl[i][j]中 
            for(int k=0;k<=j;k++)
                if(maxn<f[i-1][k]+a[i][j-k])
                    maxn=f[i-1][k]+a[i][j-k],maxx=j-k;
            f[i][j]=maxn,sl[i][j]=maxx;
        }
    cout<<f[n][m]<<endl;
    pr(n,m);
    return 0;
}
点击查看AC代码

1281:最长上升子序列

//1281:最长上升子序列
#include<iostream>
using namespace std;
int n,a[1001],b[1001],ans;
int main(){
    cin>>n;
    for(int  i=1;i<=n;i++)cin>>a[i];
    b[1]=1;
    for(int i=2;i<=n;i++)
    {
        b[i]=1;
        for(int j=1;j<i;j++)
            if(a[i]>a[j]&&b[i]<b[j]+1)
            {
                b[i]=b[j]+1;
                if(ans<b[i])ans=b[i];
            }
    }
    cout<<ans;
    return 0;
}
点击查看AC代码

1282:最大子矩阵

#include <iostream>  
#include <cstring>  
using namespace std;  
const int maxn =101;//n,m行列值最大100 
int n,m,res=-127;  //res取到最小整数就好 
int a[maxn][maxn],b[maxn],dp[maxn];  
int main()  
{  
    cin>>n;
    m=n;  
    for(int i=0;i<n;i++)  
       for(int j=0;j<m;j++)  
          cin>>a[i][j];  
    for(int x=0;x<n;x++){//设置起始行   
        memset(b,0,sizeof(b));//设置结束行   
        for(int y=x;y<n;y++)
        {  
            for(int j=0;j<m;j++)  
                b[j]+=a[y][j];//b存储第起始行x到y行到中每一列的值   
            dp[0]=b[0];
            if(dp[0]>res)//不要忘了这个   
                res=dp[0]; 
            for(int i=1;i<m;i++)
            {  
                if(dp[i-1]<0)  
                    dp[i]=b[i];  
                else   
                   dp[i]=dp[i-1]+b[i];  
                if(dp[i]>res)          //维护最后的结果   
                   res=dp[i];  
            }  

        }  
    }  
    cout<<res<<endl;  
    return 0;  
}  
点击查看AC代码

1283:登山

//1283:登山
#include<iostream>
using namespace std;
int n,sh,maxn,maxx,a[1001],b[1001][3],c[1001][3];
int main(){
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i];
    maxn=1,maxx=1;
    b[1][0]=1,b[1][1]=1,b[1][2]=1;
    for(int i=2;i<=n;i++)
    {
        b[i][0]=1;
        for(int j=1;j<i;j++)
        {
            if(a[i]>a[j]&&b[i][0]<b[j][0]+1)
            {
                b[i][0]=b[j][0]+1;
                if(b[i][0]>maxn)
                    maxn=b[i][0],maxx=i;
            }
        }
        b[i][1]=maxn,b[i][2]=maxx;
     }      
    maxn=1,maxx=1;
    c[n][0]=1,c[n][1]=1,c[n][2]=1;
    for(int i=n-1;i>=1;i--)
    {
        c[i][0]=1;
        for(int j=n;j>i;j--)
        {
            if(a[i]>a[j]&&c[i][0]<c[j][0]+1)
            {
                c[i][0]=c[j][0]+1;
                if(c[i][0]>maxn)
                    maxn=c[i][0],maxx=i;
            }
        }
        c[i][1]=maxn,c[i][2]=maxx;
     }
     maxn=0;
     for(int i=2;i<n;i++)
     {
         sh=b[i][1]+c[i][1];
        if(b[i][2]==c[i][2]||b[i][2]!=c[i][2]&&a[b[i][2]]==a[c[i][2]])sh--;
        if(maxn<sh)maxn=sh; 
     }
     cout<<maxn;
    return 0;
}
点击查看AC代码

1284:摘花生

//1284:摘花生
#include<iostream>
using namespace std;
int t,n,m,map[101][101],f[101][101];
int main(){
    cin>>t;
    for(int k=1;k<=t;k++)
    {
        cin>>n>>m;
        for(int i=1;i<=n;i++)
            for(int j=1;j<=m;j++)cin>>map[i][j];
        for(int i=1;i<=n;i++)
            for(int j=1;j<=m;j++)
                f[i][j]=max(f[i-1][j],f[i][j-1])+map[i][j];
        cout<<f[n][m]<<endl;
    }
    return 0;
}
点击查看AC代码

1285:最大上升子序列和

//1285:最大上升子序列和
#include<iostream>
using namespace std;
int n,a[1001],b[1001],ans;
int main(){
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i];
    b[1]=a[1];
    for(int i=2;i<=n;i++)
    {
        b[i]=a[i];
        for(int j=1;j<i;j++)
            if(a[i]>a[j]&&b[i]<b[j]+a[i])
            {
                b[i]=b[j]+a[i];
                if(ans<b[i])ans=b[i];
            }
    }
    cout<<ans;
    return 0;
}
点击查看AC代码

1286:怪盗基德的滑翔翼

//1286:怪盗基德的滑翔翼
#include<iostream>
using namespace std;
int k,n,a[1001],b[1001],ans;
int main(){
    cin>>k;
    for(int i=1;i<=k;i++)
    {
        cin>>n;
        for(int j=1;j<=n;j++)cin>>a[j];
        b[1]=1;
        ans=1;
        for(int j=2;j<=n;j++)
        {
            b[j]=1;
            for(int m=1;m<j;m++)
                if(a[j]<a[m]&&b[j]<b[m]+1)
                {
                    b[j]=b[m]+1;
                    if(ans<b[j])ans=b[j];
                }
        }
        for(int j=2;j<=n;j++)
        {
            b[j]=1;
            for(int m=1;m<j;m++)
                if(a[j]>a[m]&&b[j]<b[m]+1)
                {
                    b[j]=b[m]+1;
                    if(ans<b[j])ans=b[j];
                }
        }
        cout<<ans<<endl;
    }
    return 0;
}
点击查看AC代码

1287:最低通行费

//1287:最低通行费 
#include<iostream>
#include<cmath>
using namespace std;
int n,a[101][100],f[101][101]; 
int main(){
    cin>>n;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)cin>>a[i][j];
    for(int i=0;i<=n;i++)f[i][0]=f[0][i]=10000;
    f[1][0]=0;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
        {
            f[i][j]=min(f[i][j-1],f[i-1][j])+a[i][j];
        }
    cout<<f[n][n];
    return 0;
}
点击查看AC代码

1288:三角形最佳路径问题

//1288:三角形最佳路径问题
#include<iostream>
using namespace std;
int n,a[101][101],f[101][101],ans;
int main(){
    cin>>n;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=i;j++)cin>>a[i][j];
    for(int i=1;i<=n;i++)
        for(int j=1;j<=i;j++)
            f[i][j]=max(f[i-1][j],f[i-1][j-1])+a[i][j];
    for(int i=1;i<=n;i++)
        if(ans<f[n][i])ans=f[n][i];
    cout<<ans;
    return 0;
}
点击查看AC代码

1289:拦截导弹

//1289:拦截导弹
#include<iostream>
using namespace std;
int n,a[20],f[20],ans;
int main(){
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i];
    f[1]=1;
    for(int i=2;i<=n;i++)
    {
        f[i]=1;
        for(int j=1;j<i;j++)
            if(a[i]<=a[j]&&f[i]<f[j]+1)
            {
                f[i]=f[j]+1;
                if(ans<f[i])ans=f[i];
            }
    }
    cout<<ans;    
    return 0;
}
点击查看AC代码

第二节 背包问题

1267:【例9.11】01背包问题

#include<iostream>
using namespace std;
int w[31],c[31],m,n,mx,tc;
void dfs(int t0,int dp)
{
    if(t0+w[dp]<=m)
    {
        tc+=c[dp];
        if(mx<tc)mx=tc;
        if(dp>1)dfs(t0+w[dp],dp-1);
        tc-=c[dp];
    }
    if(dp>1)dfs(t0,dp-1);
    return;
}
int main(){
    cin>>m>>n;
    for(int i=1;i<=n;i++)
        cin>>w[i]>>c[i];
    dfs(0,n);
    cout<<mx;
    return 0;
}
点击查看AC代码

1268:【例9.12】完全背包问题

#include<cstdio>
#include<string.h>
#include<iostream>
using namespace std;
int M,n,w[10000],c[10000],f[10000][10000];
int main()
{
    cin>>M>>n;
    for(int i=1;i<=n;i++)
    cin>>w[i]>>c[i];
    for(int i=1;i<=n;i++)
        for(int j=1;j<=M;j++)
        {
        if(w[i]>j)f[i][j]=f[i-1][j];
            else f[i][j]=max(f[i][j-w[i]]+c[i],f[i-1][j]);
        }
    cout<<"max="<<f[n][M];
    return 0;
}
点击查看AC代码

1269:【例9.13】庆功会

#include<iostream>
using namespace std;
int a[501],b[501],c[501],f[6001];
int mx(int a,int b)
{
    if(a>=b)return a;
    else return b;
}
int main()
{
    int n,m;
    cin>>n>>m;
    for(int i=1;i<=n;i++)
    cin>>a[i]>>b[i]>>c[i];
    for(int i=1;i<=n;i++)
        for(int j=1;j<=c[i];j++)
            for(int k=m;k>=0;k--)
                if(a[i]<=k)f[k]=mx(f[k],f[k-a[i]]+b[i]);
    cout<<f[m];
    return 0;
}
点击查看AC代码

1270:【例9.14】混合背包

#include<iostream>
#include<cstdio>
using namespace std;
int main()
{    //freopen("a.txt","r",stdin);    
    int v,n;    
    while(scanf("%d%d",&v,&n)!=EOF)    
    {        
        int w[1000],c[1000],p[1000],i,k=0,t,j,f[202]={0};        
        for(i=1;i<=n;i++)        
        {    
            t=1;            
            scanf("%d%d%d",&w[i],&c[i],&p[i]);        
            if(p[i]>1)   //将有限个相同价格的物品转化为不同价格的单个物品         
            {    
                while(p[i]>t)        
                {
                    k++;                    
                    w[n+k]=w[i]*t;                    
                    c[n+k]=c[i]*t;                    
                    p[n+k]=1;                    
                    p[i]-=t;                
                    t*=2;                
                }                
                w[i]*=p[i];                
                c[i]*=p[i];                
                p[i]=1;
            }        
        }        
        for(i=1;i<=n+k;i++)         
        if(p[i]==1)   //判断是01背包还是完全背包          
            for(j=v;j>=w[i];j--)          
                f[j]=f[j]>f[j-w[i]]+c[i] ? f[j]:f[j-w[i]]+c[i];        
        else          
            for(j=w[i];j<=v;j++)          
                f[j]=f[j]>f[j-w[i]]+c[i] ? f[j]:f[j-w[i]]+c[i];    
        printf("%d\n",f[v]);
    }    
    return 0;
}
点击查看AC代码

1271:【例9.15】潜水员

#include<iostream>
#include<cstring>
using namespace std;
int f[101][101],a[5000],b[5000],c[5000];
int main()
{
    int O,N,n;
    memset(f,127,sizeof(f));
    cin>>O>>N>>n;
    for(int i=1;i<=n;i++)
        cin>>a[i]>>b[i]>>c[i];
    f[0][0]=0; 
    for(int i=1;i<=n;i++)
    {
        for(int j=O;j>=0;j--)
        {
            for(int t=N;t>=0;t--)
            {
               int O1=j+a[i];
               if(O1>=O)O1=O;
               int N1=t+b[i];
               if(N1>=N)N1=N; 
               if(f[O1][N1]>f[j][t]+c[i])f[O1][N1]=f[j][t]+c[i];
            }
        }
    }
    cout<<f[O][N];
    return 0;
}
点击查看AC代码

1272:【例9.16】分组背包

#include<bits/stdc++.h>
using namespace std;
int dp[205];
int v, n, t;
int we[35], c[35];
vector<int>ve[35];
int main()
{   //freopen("in.txt", "r", stdin);
    //freopen("out.txt", "w", stdout);
    int p;
    cin >> v >> n >> t;
    for(int i = 1; i <= n; i++)
    {   scanf("%d%d%d", &we[i], &c[i], &p);
        ve[p].push_back(i);
    }
    for(int i = 1; i <= t; i++)
    {   for(int j = v; j >= 0; j--)
        {
            for(int k = 0; k < ve[i].size(); k++) {
                int x = ve[i][k];
                if (j >= we[x])
                    dp[j] = max(dp[j], dp[j-we[x]]+c[x]);
            }
        }
    }
    printf("%d\n", dp[v]);
    return 0;
}
点击查看AC代码

1273:【例9.17】货币系统

#include<iostream>
using namespace std;
int n,m,a[101];
long long f[10001]; 
int main(){
    cin>>n>>m;
    for(int i=1;i<=n;i++)cin>>a[i];
    f[0]=1;
    for(int i=1;i<=n;i++)
        for(int j=0;j<=m-a[i];j++)
            f[j+a[i]]+=f[j];
    cout<<f[m];
    return 0;
}
点击查看AC代码

1290:采药

//1290:采药 
#include<iostream>
using namespace std;
int tt,n,w[101],v[101],f[10001]; 
int main(){
    cin>>tt>>n;
    for(int i=1;i<=n;i++)cin>>w[i]>>v[i];
    for(int i=1;i<=n;i++)
        for(int j=tt;j>0;j--)
            if(j>=w[i])
            f[j]=max(f[j],f[j-w[i]]+v[i]);
    cout<<f[tt];
    return 0;
}
点击查看AC代码

1291:数字组合

//1291:数字组合
#include<iostream>
using namespace std;
int n,m,a[21];
long long f[20001]; 
int main(){
    cin>>n>>m;
    for(int i=1;i<=n;i++)cin>>a[i];
    f[0]=1;
    for(int i=1;i<=n;i++)
        for(int j=m;j>=a[i];j--)
            f[j]+=f[j-a[i]];
    cout<<f[m];
    return 0;
}
点击查看AC代码

1292:宠物小精灵之收服

//1292:宠物小精灵之收服
#include<iostream>
using namespace std;
int f[1010][1010],n,m,k,i,j,l,a,b;
int main()
{
    cin>>n>>m>>k;
    for(int l=1;l<=k;l++)
    {
        cin>>a>>b;
        for(int i=n;i>=a;i--)
            for(int j=m;j>=b;j--)
                if(f[i][j]<f[i-a][j-b]+1)
                    f[i][j]=f[i-a][j-b]+1;
    }
    cout<<f[n][m]<<' ';
    i=m;
    while(i>=0&&f[n][i]==f[n][m])i--;
    cout<<m-i-1;
 } 
点击查看AC代码

1293:买书

//1293:买书
#include<iostream>
using namespace std;
int n=4,m,a[4]={10,20,50,100};
long long f[10001]; 
int main(){
    cin>>m;
    f[0]=1;
    for(int i=0;i<n;i++)
        for(int j=a[i];j<=m;j++)
            f[j]+=f[j-a[i]];
    cout<<f[m];
    return 0;
}
点击查看AC代码

1294:Charm Bracelet

//1294:Charm Bracelet
#include<iostream>
using namespace std;
int n,m,w[3501],v[3501],f[12881];
int main(){
    cin>>n>>m;
    for(int i=1;i<=n;i++)cin>>w[i]>>v[i];
    for(int i=1;i<=n;i++)
        for(int j=m;j>=w[i];j--)
            if(f[j]<f[j-w[i]]+v[i])f[j]=f[j-w[i]]+v[i];
    cout<<f[m];
    return 0;
}
点击查看AC代码

1295:装箱问题

//1295:装箱问题
#include<iostream>
using namespace std;
int n,m,w[31],f[20001];
int main(){
    cin>>m>>n;
    for(int i=1;i<=n;i++)cin>>w[i];
    for(int i=1;i<=n;i++)
        for(int j=m;j>=w[i];j--)
            if(f[j]<f[j-w[i]]+w[i])f[j]=f[j-w[i]]+w[i];
    cout<<m-f[m];
    return 0;
}
点击查看AC代码

1296:开餐馆

//1296:开餐馆
#include<iostream>
#include<cmath>
#include<cstring>
using namespace std;
int a[100],b[101],f[101],ans;
int t,n,k,m;
int main(){
    cin>>t;
    for(int l=1;l<=t;l++)
    {
        memset(a,0,sizeof(a));
        memset(f,0,sizeof(f));
        ans=0;
        cin>>n>>k;
        for(int i=1;i<=n;i++)cin>>a[i];
        for(int i=1;i<=n;i++)cin>>b[i];
        for(int i=1;i<=n;i++)
        {
            f[i]=b[i];
            for(int j=1;j<i;j++)
                if(a[i]-a[j]>k)
                    f[i]=max(f[i],f[j]+b[i]);
            if(ans<f[i])ans=f[i];
        }
        cout<<ans<<endl;
    }
    return 0;
}
点击查看AC代码

第三节 动态规划经典题

1274:【例9.18】合并石子

#include<iostream>
#include<cstring>
using namespace std;
int a[101],f[101][101],s[101]; 
int main()
{
    int n;
    cin>>n;
    memset(f,1,sizeof(f));
    for(int i=1;i<=n;i++)
    {
        cin>>a[i];
        f[i][i]=0;
        s[i]=s[i-1]+a[i];
    }
    for(int i=n;i>0;i--)
        for(int j=i+1;j<=n;j++)
            for(int k=i;k<j;k++)
                if(f[i][j]>f[i][k]+f[k+1][j]+s[j]-s[i-1])
                    f[i][j]=f[i][k]+f[k+1][j]+s[j]-s[i-1];
    cout<<f[1][n]<<endl;
     return 0;
}
点击查看AC代码

1275:【例9.19】乘积最大

//1275:【例9.19】乘积最大
#include<iostream>
using namespace std;
int n,k,a[11],b[11][11],f[11][11];
char ch;
int main(){
    cin>>n>>k;
    for(int i=1;i<=n;i++)
    {
        cin>>ch;
        a[i]=ch-'0';
    }
    for(int i=1;i<=n;i++)
    {
        b[i][i]=a[i];
        for(int j=i+1;j<=n;j++)
                b[i][j]=b[i][j-1]*10+a[j];
    }
    for(int i=1;i<=n;i++)f[i][0]=b[1][i];
    for(int j=1;j<=k;j++)
        for(int i=j+1;i<=n;i++)
            for(int l=j;l<i;l++)
                f[i][j]=max(f[i][j],f[l][j-1]*b[l+1][i]);
    cout<<f[n][k];
    return 0;
}
点击查看AC代码

1276:【例9.20】编辑距离

//1276:【例9.20】编辑距离
#include<iostream>
using namespace std;
string s1,s2;
int f[2001][2001];
int mmin(int x,int y,int z)
{
    if(x>y)swap(x,y);
    if(x>z)swap(x,z);
    return x;
}
int main(){
    cin>>s1>>s2;
    int l1=s1.size(),l2=s2.size();
    for(int i=1;i<=l1;i++)f[i][0]=i;
    for(int i=1;i<=l2;i++)f[0][i]=i;
    for(int i=1;i<=l1;i++)
        for(int j=1;j<=l2;j++)
        {
            if(s1[i-1]==s2[j-1])f[i][j]=f[i-1][j-1];
            else f[i][j]=mmin(f[i-1][j],f[i][j-1],f[i-1][j-1])+1;
        }
    cout<<f[l1][l2];
    return 0;
}
点击查看AC代码

1277:【例9.21】方格取数

//1277:【例9.21】方格取数
#include<iostream>
using namespace std;
int n,a[11][11],b[11][11][11][11];
int main(){
    cin>>n;
    int x,y,z;
    while(cin>>x>>y>>z)
    {
        if(x==0&&y==0&&z==0)break;
        a[x][y]=z;
    }
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            for(int k=1;k<=n;k++)
                for(int l=1;l<=n;l++)
                {
                    int tmp1=max(b[i-1][j][k][l-1],b[i-1][j][k-1][l]);
                    int tmp2=max(b[i][j-1][k][l-1],b[i][j-1][k-1][l]);
                    b[i][j][k][l]=max(tmp1,tmp2)+a[i][j];
                    if(i!=k&&j!=l)b[i][j][k][l]+=a[k][l];
                 } 
    cout<<b[n][n][n][n];
    return 0;
}
点击查看AC代码

1278:【例9.22】复制书稿(book)

//1278:【例9.22】复制书稿(book)
#include<iostream>
using namespace std;
int m,k,a[501],f[501][501],sum[501];
int maxx(int x,int y) { return x>y?x:y; } 
int minn(int x,int y) { return x<y?x:y; } 
void pr(int x,int y)
{
    if(x<1)return;
    if(y==1)
    {
        cout<<1<<' '<<x<<endl;
        return;
    }    
    int pd=x,pdz=a[x];
    while(pdz<=f[m][k]&&pd>=1)//从最后一个人最后一本书开始,只要不超量就让他写 
    {
        pdz+=a[pd-1];
        pd--;
    }
    pr(pd,y-1);
    cout<<pd+1<<' '<<x<<endl;
    return;
}
int main(){
    cin>>m>>k;
    for(int i=1;i<=m;i++)
        for(int j=1;j<=k;j++)
            f[i][j]=1e6;
    for(int i=1;i<=m;i++)
    {
        cin>>a[i];
        sum[i]=sum[i-1]+a[i];
        f[i][1]=sum[i];
    }
    for(int j=2;j<=k;j++)
        for(int i=j;i<=m;i++)
            for(int l=j-1;l<i;l++)
            {
                int tmp=maxx(f[l][j-1],sum[i]-sum[l]);
                f[i][j]=minn(f[i][j],tmp);
            }
    pr(m,k);
    return 0;
}
点击查看AC代码

1279:【例9.23】橱窗布置(flower)

//1279:【例9.23】橱窗布置(flower)
#include<iostream>
using namespace std;
int f,v,a[101][101],c[101][101],d[101][101];
int mmax(int x,int y){return x>y?x:y;}
void pr(int x,int y)
{
    if(x==1)cout<<d[1][y];
    else
    {
        pr(x-1,d[x][y]-1);
        cout<<' '<<d[x][y];
    }
    return;
}
int main(){
    cin>>f>>v;
    for(int i=1;i<=f;i++)
        for(int j=1;j<=v;j++)cin>>a[i][j],c[i][j]=-1e7;
    for(int i=0;i<=v;i++)c[0][i]=0;
    for(int i=1;i<=f;i++)
        for(int j=i;j<=v;j++)
            for(int k=i;k<=j;k++)
            {
                if(c[i][j]<c[i-1][k-1]+a[i][k])
                    c[i][j]=c[i-1][k-1]+a[i][k],d[i][j]=k;
            }
    cout<<c[f][v]<<endl;
    pr(f,v);
    return 0;
}
点击查看AC代码

1280:【例9.24】滑雪

//1280:【例9.24】滑雪
#include<iostream>
using namespace std;
int r,c,a[101][101],f[101][101],ans;
int dx[]={1,0,-1,0};
int dy[]={0,1,0,-1};
int dfs(int x,int y)
{
    if(f[x][y])return f[x][y];
    f[x][y]=1;
    for(int i=0;i<4;i++)
    {
        int tx=x+dx[i],ty=y+dy[i];
        if(tx>=1&&tx<=r&&ty>=1&&ty<=c&&a[x][y]>a[tx][ty])
        {
            int tmp=dfs(tx,ty)+1;
            if(f[x][y]<tmp)f[x][y]=tmp;
        }
    }
    return f[x][y];
}
int main(){
    cin>>r>>c;
    for(int i=1;i<=r;i++)
        for(int j=1;j<=c;j++)cin>>a[i][j];
    for(int i=1;i<=r;i++)
        for(int j=1;j<=c;j++)
            dfs(i,j);
    for(int i=1;i<=r;i++)
        for(int j=1;j<=c;j++)
            if(ans<f[i][j])ans=f[i][j];
    cout<<ans;
    return 0;
}
点击查看AC代码

1297:公共子序列

//1297:公共子序列
#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
int f[1001][1001];
int ggxl(string sa,string sb)
{
    int la=sa.size(),lb=sb.size();
    for(int i=1;i<=la;i++)
        for(int j=1;j<=lb;j++)
        {
            f[i][j]=max(f[i-1][j],f[i][j-1]);
            if(sa[i-1]==sb[j-1])f[i][j]=max(f[i][j],f[i-1][j-1]+1);
        }
    return f[la][lb];
}
int main(){
    string s1,s2;
    while(cin>>s1>>s2)
    {
        memset(f,0,sizeof(f));
        cout<<ggxl(s1,s2)<<endl;
    }
    return 0;
}
点击查看AC代码

1298:计算字符串距离

//1298:计算字符串距离
#include<iostream>
#include<cstring>
using namespace std;
string s1,s2;
int f[1001][1001];
int mmin(int a,int b,int c)
{
    if(a>b)swap(a,b);
    if(a>c)swap(a,c);
    return a;
}
int edstr(string x,string y)
{
    int l1=x.size(),l2=y.size();
    for(int i=1;i<=l1;i++)f[i][0]=i;
    for(int i=1;i<=l2;i++)f[0][i]=i;
    for(int i=1;i<=l1;i++)
        for(int j=1;j<=l2;j++)
        {
            if(x[i-1]==y[j-1])f[i][j]=f[i-1][j-1];
            else f[i][j]=mmin(f[i-1][j],f[i][j-1],f[i-1][j-1])+1;
        }
    return f[l1][l2];
}
int main(){
    int n;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>s1>>s2;
        cout<<edstr(s1,s2)<<endl;
    }
    return 0;
}
点击查看AC代码

1299:糖果

//1299:糖果
#include<iostream>
using namespace std;
int n,m,x,f[101][101];
int main(){
    cin>>n>>m;
    for(int i=1;i<=n;i++)
    {
        cin>>x;
        f[i][x%m]=x;
        for(int j=0;j<m;j++)
            if(f[i-1][j])f[i][(j+x)%m]=f[i-1][j]+x;        
        for(int j=0;j<m;j++)
            if(f[i][j]<f[i-1][j])f[i][j]=f[i-1][j];
    }
    cout<<f[n][0];
    return 0;
}
点击查看AC代码

1300:鸡蛋的硬度

//1300:鸡蛋的硬度 
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
int f[110][11];
int main()
{
    int n,m;
    while(scanf("%d%d",&n,&m)!=EOF)
    {
        memset(f,0,sizeof(f));
        for(int i=1;i<=n;i++)
            for(int j=1;j<=m;j++)
                f[i][j]=i;
        for(int j=1;j<=n;j++)
            for(int i=2;i<=m;i++)
                for(int k=1;k<=j;k++)//枚举
                    f[j][i]=min(f[j][i],max(f[k-1][i-1],f[j-k][i])+1);
        /*在1~j层楼间选择第k层扔下鸡蛋,如果破了,说明硬度介于1~k-1之间 ,
        问题变成用i-1个鸡蛋去测k-1层楼的硬度。如果没破则说明硬度介于k~j之间,
        问题变成用i个鸡蛋去测j-k层楼的硬度,题目要求是最坏的情况下,故要取两者最大值 */ 
        printf("%d\n",f[n][m]);
    }
    return 0;
}
点击查看AC代码

1301:大盗阿福

//1301:大盗阿福 
#include<iostream>
using namespace std;
int t,n,a[100001],f[100001],ans; 
int maxx(int x,int y){return x>y?x:y;}
int main(){
    cin>>t;
    for(int l=1;l<=t;l++)
    {
        cin>>n;
        for(int i=1;i<=n;i++)cin>>a[i];
        f[1]=a[1];
        for(int i=2;i<=n;i++)
            f[i]=maxx(f[i-1],f[i-2]+a[i]);
        cout<<f[n]<<endl;
    }
    return 0;
}
点击查看AC代码

1302:股票买卖

#include<bits/stdc++.h>

using namespace std;

const int MAX_NUM = 100005;
int price[MAX_NUM];
int pre[MAX_NUM];
int post[MAX_NUM];

int max_profit;

int main()
{
    int num;
    scanf("%d",&num);
    while (num--)
    {
        int days;
        //memset(price, 0, sizeof(price));
        memset(pre, 0, sizeof(pre));
        memset(post, 0, sizeof(post));
        scanf("%d",&days);
        for (int i = 0; i < days; i++)
        {
            scanf("%d",&price[i]);
        }
        //前i天中价格最小的一天买,第i天卖获取的最大利润
        //初始化,计算pre
        pre[0] = 0;
        int min_price = price[0];
        for (int i = 1; i<days; i++)
        {
             pre[i] = max(pre[i - 1], price[i] - min_price);
            if (min_price>price[i])
                min_price = price[i];
        }
        //第j天买,之后寻找卖的一天,获取最大利润
        //初始化,并且计算post
        post[days - 1] = 0;//初始化为0
        int max_price = price[days-1];
        for (int j = days - 2; j >= 0; j--)
        {
            post[j] = max(post[j + 1], max_price - price[j]);
            if (max_price < price[j])
                max_price = price[j];
        }
        //进行遍历,输出最大值
        max_profit = pre[0] + post[0];
        for (int k = 0; k < days; k++)
        {
            max_profit = max(pre[k] + post[k],max_profit);
        }
        cout << max_profit << endl;
    }
    return 0;
}
点击查看AC代码

1303:鸣人的影分身

#include<iostream>
using namespace std;
int main()
{ int t,m,n,i,j,a[100][100];
  for(i=0;i<11;i++)
 { a[0][i]=1;
   a[i][0]=0;
 }
  for(i=1;i<11;i++)
  for(j=1;j<11;j++)
      if(j-1>=0&&i-j>=0)a[i][j]=a[i][j-1]+a[i-j][j];
    else if(j-1<0&&i-j>=0)a[i][j]=a[i-j][j];
    else if(j-1>=0&&i-j<0)a[i][j]=a[i][j-1];
 
  cin>>t;
  while(t--)
  { cin>>m>>n;
    cout<<a[m][n]<<endl;
  }
}
点击查看AC代码

1304:数的划分

#include<iostream>
using namespace std;
int ans,a[100]={1},n,k;
void dfs(int n,int dp)
{
    if(dp==k)
    {
        ans++;
        return;
    } 
    for(int i=a[dp-1];i*(k+1-dp)<=n;i++)
    {
        a[dp]=i;
        dfs(n-i,dp+1);
    }
 } 
int main(){
    cin>>n>>k;
    dfs(n,1);
    cout<<ans;
    return 0;
}
点击查看AC代码

1305:Maximum sum

//1305:Maximum sum 
#include<iostream>
using namespace std;
int t,n,a[50005],lsum[50005],rsum[50005],lmx[50005],rmx[50005],lmax,rmax,maxx; 
int main(){
    cin>>t;
    for(int l=1;l<=t;l++)
    {
        cin>>n;
        lmax=rmax=maxx=-1e6;
        rsum[n+1]=0;
        for(int i=1;i<=n;i++)
        {
            cin>>a[i];
            if(lsum[i-1]>=0)lsum[i]=lsum[i-1]+a[i];
            else lsum[i]=a[i];
            if(lmax<lsum[i])lmax=lsum[i];
            lmx[i]=lmax;
        }
        for(int i=n;i>0;i--)
        {
            if(rsum[i+1]>=0)rsum[i]=rsum[i+1]+a[i];
            else rsum[i]=a[i];
            if(rmax<rsum[i])rmax=rsum[i];
            rmx[i]=rmax;
        }
        for(int i=1;i<n;i++)
            if(maxx<lmx[i]+rmx[i+1])maxx=lmx[i]+rmx[i+1];
        cout<<maxx<<endl;
    }
    return 0;
}
点击查看AC代码

1306:最长公共子上升序列

#include <cstdio>
#include <iostream>
#include <vector> 
#define INF 1e9
using namespace std;
struct nod
{
    int val;
    vector<int>v;
}f[505];
int a[505],b[505];
int main()
{
    int n,m,i,j;
    scanf("%d",&m);
    for (i=1;i<=m;i++) scanf("%d",&a[i]);
    scanf("%d",&n);
    for (i=1;i<=n;i++) scanf("%d",&b[i]);
    for (i=1;i<=n;i++) 
    {
        nod k;
        k.val=0;
        for (j=1;j<=m;j++)
        {
            if (b[i]>a[j] && k.val<f[j].val) k=f[j];    
            if (b[i]==a[j]) 
            {
                f[j].val=k.val+1;
                f[j].v=k.v;
                f[j].v.push_back(b[i]);
            }
        }  
    }
    nod Max = f[1];  
    for (int i=2;i<=m;i++)
        if (f[i].val>Max.val) Max = f[i];  
    printf("%d\n",Max.val);
    for (int i =0; i < Max.v.size(); i++)  
        printf("%d ",Max.v[i]);
    printf("\n");
} 
点击查看AC代码

第三部分 数据结构

第一章 栈

1331:【例1-2】后缀表达式的值

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
long long a[1001],top,tp;
char b[1001];
int main()
{
    int flag=1;//值为1表示正常情况,-1表示正在输入一个负数,0则表示刚输入一个“-”,是负号还是减号待定
    long long ts=0;
    char ch;
    while(ch=getchar())
    {
        if(ch>='0'&&ch<='9')
        {
            if(flag==0)flag=-1;
            ts=ts*10+ch-'0';
        }
        else
        {
             if(flag==0)
            {
                b[++tp]='-';
                flag=1; 
            }
            if(ch=='@')break;    
            if(ch=='-')flag=0;
            else if(ch==' ')
            {
                ts*=flag;
                a[++top]=ts;
                flag=1;
                ts=0;
            }
            else b[++tp]=ch;
        }
     } 
     for(int i=1;i<=tp;i++)
     {
         ch=b[i];
         ts=a[top--];
         switch(ch)
         {
             case '+':a[top]+=ts;break;
             case '-':a[top]-=ts;break;
             case '*':a[top]*=ts;break;
             default:a[top]/=ts;
         }
     }
    cout<<a[top]<<endl;
     return 0;
}
点击查看AC代码

1353:表达式括号匹配(stack)

#include<iostream>
using namespace std;
int top;
int main(){
    string s; 
    getline(cin,s,'@');
    int l=s.size() ;
    for(int i=0;i<l;i++)
    if(s[i]=='(')top++;
    else if(s[i]==')')if(top<1)
    {
        cout<<"NO";
        return 0;
    }
    else top--;
    if(top)cout<<"NO";
    else cout<<"YES";
    return 0;
}
点击查看AC代码

1354:括弧匹配检验

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
int top;
char a[1000];
int main(){
    char s[1000]; 
    gets(s);
    int l=strlen(s);
    for(int i=0;i<l;i++)
    if(s[i]=='('||s[i]=='[')a[++top]=s[i];
    else if(s[i]==')')
        if(top==0||a[top]!='(')
        {
            cout<<"Wrong";
            return 0;
        }
        else top--;
    else if(s[i]==']')
        if(top==0||a[top]!='[')
        {
            cout<<"Wrong";
            return 0;
        }
        else top--;
    
    if(top)cout<<"Wrong";
    else cout<<"OK";
    return 0;
}
点击查看AC代码

1355:字符串匹配问题(strs)

#include<cstdio>
#include<iostream>
#include<cstring>
using namespace std;
char a[]={'{','[','(','<','}',']',')','>'};//{→0 [→1 (→2 <→3 }→4 ]→5 )→6 >→7
char str[300];
int b[300],stack[300];
int main()
{
    int n;
    int k;
 
    cin>>n;//输入测试数据组数
    while(n--)
    {
        int top=0;
        bool flag=true;//用于判断嵌套是否合法的标记
 
        cin>>str;
        int len=strlen(str);
        for(int i=0;i<len;i++)
            for(int j=0;j<8;j++)
                if(str[i]==a[j])
                {
                    b[i]=j;////建立映射
                    break;//跳出内循环
                }
 
        for(int i=0;i<len;i++)//判断是否匹配
        {
            if(b[i]<=3)//b[i]元素入栈
            {
                if(top==0||b[i]>=stack[top])//b[i]元素可以入栈
                {
                    top++;
                    stack[top]=b[i];
                }
                else//元素无法入栈,说明该组数据非法
                {
                    flag=false;
                    break;
                }
            }
            else if(b[i]>=4)//判断是否配对
            {
                if(top>0&&stack[top]+4==b[i])//可以配对
                    top--;
                else//无法配对
                {
                    flag=false;
                    break;
                }
            }
        }
        if(top)
            cout<<"NO"<<endl;//栈内有元素,匹配不成功
        else if(flag==1)
            cout<<"YES"<<endl;//栈内无元素,匹配成功
        else
            cout<<"NO"<<endl;//栈内无元素,匹配不成功
    }
    return 0;
}
点击查看AC代码

1356:计算(calc)

//1356:计算(calc)
/*基本思路:后面优先级高,前面内容入栈,否则先算前面内容*/ 
#include<iostream>
#include<stack>
#include<cmath>
#include<cstring> 
using namespace std;
int const N=1e5+1;
int x,y;
char ch,ch0; 
string s;
stack<int>s1;
stack<char>s2;
//计算运算优先组,后面优先级高就前面内容入栈,后面优先级小于等于前面优先组就先算栈内内容 
int level(char p)
{
    if(p=='+'||p=='-')return 1;
    if(p=='*'||p=='/')return 2;
    if(p=='^')return 3;    
    return 0;
}

//完成一次基本计算 
void calc()
{
    int m,n;
    char z;
    n=s1.top();
    s1.pop();
    m=s1.top();
    s1.pop();
    z=s2.top();
    s2.pop();
    switch(z)
    {
        case '+':s1.push(m+n);break;
        case '-':s1.push(m-n);break;
        case '*':s1.push(m*n);break;
        case '/':s1.push(m/n);break;
        default:s1.push(pow(m,n));
    }
    return;
}
int main(){    
    cin>>s;
    s='('+s+')';
    int i=0;
    ch='(';
    do
    {
        if(ch=='(')
        {
            s2.push('(');
        }
        
        //遇到)就计算到(为止。遇到(之前,栈内所存运算符应该逐级上升,故需反向运算
        //如1+2*3^4 
        else if(ch==')')
        {
            while(s2.top()!='(')calc();
            s2.pop();//弹出( 
        }
        else if(ch>='0'&&ch<='9'||ch=='-'&&s[i-1]=='(') 
        //读到的是数字,把连续的数字变成数值 ,如果是'-'先判断前面是不是(,是则说明是负号不是减号 
        {
            if(ch=='-')x=0,y=-1;//是负号则符号设为-1,初始值为0 
            else x=ch-'0',y=1;//默认符号为正
            ch0=s[++i];
            while(ch0>='0'&&ch0<='9')x=x*10+ch0-'0',ch0=s[++i];
            i--;
            x*=y;
            s1.push(x);
        }
        else  //ch为运算符 
        {
            while(level(ch)<=level(s2.top()))//当前运算符不超过栈顶运算,先算栈顶运算 
            {
                calc();
            }
            s2.push(ch);//直到当前运算符高于栈顶运算符再把运算符存栈 
        }
    }while(ch=s[++i]);
    cout<<s1.top()<<endl;
    return 0;
}
点击查看AC代码

1357:车厢调度(train)

#include<bits/stdc++.h>
using namespace std;
int a[1001],b[1001];
int main(){
    std::ios::sync_with_stdio(false);
    int n;
    cin>>n;
    for(int i=1;i<=n;i++)cin>>a[i];
    int j=0,k=1;
    for(int i=1;i<=n;i++)
    {
        while(k<a[i])b[++j]=k++;
        if(k==a[i])k++;
         else if(b[j]==a[i]&&j>0)j--;
         else {
             cout<<"NO";
             return 0;
         }
    }
    cout<<"YES";
    return 0;
}
点击查看AC代码

1358:中缀表达式值(expr)

//1358:中缀表达式值(expr)
/*基本思路:后面优先级高,前面内容入栈,否则先算前面内容*/ 
#include<iostream>
#include<stack>
#include<cmath>
#include<cstring> 
using namespace std;
int const N=1e5+1;
int x,y;
char ch,ch0; 
string s;
stack<int>s1;
stack<char>s2;
//计算运算优先组,后面优先级高就前面内容入栈,后面优先级小于等于前面优先组就先算栈内内容 
bool chkh()
{
    for(int i=0;i<s.size();i++)
        if(s[i]=='(')s2.push('(');
        else if(s[i]==')'||i==s.size()-1&&s[i]=='@')
            if(s2.empty())return false;
            else s2.pop();
    if(s2.empty())return true;
    else return false;
}
int level(char p)
{
    if(p=='+'||p=='-')return 1;
    if(p=='*'||p=='/')return 2;
    if(p=='^')return 3;    
    return 0;
}
bool chfh()
{
    for(int i=1;i<s.size();i++)
        if(level(s[i])>0&&level(s[i-1])>0)
            return false;
    return true;
}

//完成一次基本计算 
void calc()
{
    int m,n;
    char z;
    n=s1.top();
    s1.pop();
    m=s1.top();
    s1.pop();
    z=s2.top();
    s2.pop();
    switch(z)
    {
        case '+':s1.push(m+n);break;
        case '-':s1.push(m-n);break;
        case '*':s1.push(m*n);break;
        case '/':s1.push(m/n);break;
        default:s1.push(pow(m,n));
    }
    return;
}
int main(){    
    cin>>s;
    s='('+s;
    if(s[s.size()-1]!='@'||!chkh()||!chfh())
    {
        cout<<"NO\n";
        return 0;
    }
    s[s.size()-1]=')';
    int i=0;
    ch='(';
    do
    {
        if(ch=='(')
        {
            s2.push('(');
        }
        
        //遇到)就计算到(为止。遇到(之前,栈内所存运算符应该逐级上升,故需反向运算
        //如1+2*3^4 
        else if(ch==')')
        {
            while(s2.top()!='(')calc();
            s2.pop();//弹出( 
        }
        else if(ch>='0'&&ch<='9'||ch=='-'&&s[i-1]=='(') 
        //读到的是数字,把连续的数字变成数值 ,如果是'-'先判断前面是不是(,是则说明是负号不是减号 
        {
            if(ch=='-')x=0,y=-1;//是负号则符号设为-1,初始值为0 
            else x=ch-'0',y=1;//默认符号为正
            ch0=s[++i];
            while(ch0>='0'&&ch0<='9')x=x*10+ch0-'0',ch0=s[++i];
            i--;
            x*=y;
            s1.push(x);
        }
        else  //ch为运算符 
        {
            while(level(ch)<=level(s2.top()))//当前运算符不超过栈顶运算,先算栈顶运算 
            {
                calc();
            }
            s2.push(ch);//直到当前运算符高于栈顶运算符再把运算符存栈 
        }
    }while(ch=s[++i]);
    cout<<s1.top()<<endl;
    return 0;
}
点击查看AC代码

第二章 队列

1332:【例2-1】周末舞会

#include<bits/stdc++.h>
using namespace std;

int main(){
    std::ios::sync_with_stdio(false);
    int l,n,b[1000],g[1000],m,lh,lt,nh,nt,boy,girl;
    cin>>l>>n>>m;
    for(int i=1;i<=l;i++)b[i]=i;
    for(int i=1;i<=n;i++)g[i]=i;
    lh=nh=1;
    lt=l;
    nt=n;
    for(int i=1;i<=m;i++){
        boy=b[lh++];
        girl=g[nh++];
        cout<<boy<<' '<<girl<<endl;
        b[++lt]=boy;
        g[++nt]=girl;
    } 
    return 0;
}
点击查看AC代码

1333:【例2-2】Blah数集

#include<iostream>
using namespace std;
const int N=1000001;
int main(){
    int a,n,num=1;
    long long q[N],p[N];
    //freopen("blash.in","r",stdin);
    while(cin>>a>>n)
    {
        q[1]=a;
        int s=1,two=1,tree=1;
        long long t;
        while(s<n){
            long long t1=q[two]*2+1,t2=q[tree]*3+1;
            if(t1<t2){
                t=t1;
                two++;
            }
            else if(t1>t2){
                t=t2;
                tree++;
            } 
            else {
                t=t1;
                two++;
                tree++;
            }
            q[++s]=t;
        } 
        p[num++]=q[n];
    } 
    for(int i=1;i<num;i++)
        cout<<p[i]<<endl;
    return 0;
}
点击查看AC代码

1334:【例2-3】围圈报数

//1334:【例2-3】围圈报数 
#include<iostream>
using namespace std;
int n,m,a[1000001][2];
int main()
{
    cin>>n>>m;
    for(int i=1;i<=n;i++)a[i][0]=i,a[i][1]=i+1;
    a[n][1]=1;
    int pr=n,cu=1,num=0;
    while(n)
    {
        num++;
        if(num==m)
        {
            a[pr][1]=a[cu][1];
            n--;
            num=0;            
            cout<<a[cu][0]<<' ';
        }
        else pr=cu;
        cu=a[cu][1];
        
    }
    return 0;
}
点击查看AC代码

1335:【例2-4】连通块

#include<iostream>
using namespace std;
int n,m,ans,tmp,a[110][110],que[110*110][2];
int fx[4][2]={{-1,0},{1,0},{0,-1},{0,1}};
void bfs(int x,int y){
    int head=0,tail=1,curx,cury;
    que[0][0]=x,que[0][1]=y;
    while(head<tail){
        curx=que[head][0];
        cury=que[head++][1];
        for(int i=0;i<4;i++){
            int tmpx=curx+fx[i][0];
            int tmpy=cury+fx[i][1];
            if(a[tmpx][tmpy]) {
                que[tail][0]=tmpx;
                que[tail++][1]=tmpy;
                a[tmpx][tmpy]=0;
            }
        } 
    }
}
int main(){
    //freopen("blacks.in","r",stdin);
    cin>>n>>m;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)cin>>a[i][j];
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)
            if(a[i][j]){
                ++ans;
                bfs(i,j);
            }
    cout<<ans<<endl; 
    return 0;
}
点击查看AC代码

1359:围成面积

//1359:围成面积 
#include<iostream>
using namespace std;
int const n=10,m=10;
int a[n+2][m+2],ans; 
int dx[]={1,0,-1,0};
int dy[]={0,-1,0,1};
void dfs(int x,int y)
{
    a[x][y]=1;
    for(int i=0;i<4;i++)
    {
        int tx=x+dx[i],ty=y+dy[i];
        if(!a[tx][ty])dfs(tx,ty);
    }
    return;
}
int main(){
    for(int i=0;i<=n+1;i++)
        for(int j=0;j<=m+1;j++)a[i][j]=-1;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)cin>>a[i][j];
    for(int i=1;i<=n;i++)
    {
        if(!a[i][1])dfs(i,1);
        if(!a[i][m])dfs(i,m);
    }
    for(int i=2;i<m;i++)
    {
        if(!a[1][i])dfs(1,i);
        if(!a[n][i])dfs(n,i);
    }
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)
            if(!a[i][j])ans++;
    cout<<ans;
    return 0;
}
点击查看AC代码

1360:奇怪的电梯(lift)

#include<bits/stdc++.h>
using namespace std;
int a[201],que[201],p[201],m[201];
int bfs(int n,int s,int b)
{
    if(s==b)return 0;
    int h=0,t=0,cx,tx;
    que[0]=s,p[s]=1,m[s]=0;
    while(h<=t)
    {
        cx=que[h];
        tx=cx+a[cx];
        if(tx==b)return m[cx]+1;
        if(tx<=n&&p[tx]==0)
        {
            que[++t]=tx;
            m[tx]=m[cx]+1;
            p[tx]=1;
        }
        tx=cx-a[cx];
        if(tx==b)return m[cx]+1;
        if(tx>0&&p[tx]==0)
        {
            que[++t]=tx;
            m[tx]=m[cx]+1;
            p[tx]=1;
        }
        h++;
    }
    return -1;
}
int main(){
    int n,s,b;
    cin>>n>>s>>b;
    for(int i=1;i<=n;i++)cin>>a[i];
    cout<<bfs(n,s,b);
    return 0;
}
点击查看AC代码

1361:产生数(Produce)

//1361:产生数(Produce)
#include<iostream>
using namespace std;
int n,k,x1,x2,p[10000],gz[16][2],que[10000],ans=1;
int f(int n,int x,int y)//把数n的倒数第x位换成y,如12345的倒数第2位换在6即得12365 
{
    int t=1;
    for(int i=1;i<x;i++)t*=10;
    return n/10/t*10*t+y*t+n%t;
}
void bfs(int x)
{
    que[0]=x;
    int h=0,t=0,cx,tx,tcx;
    while(h<=t)
    {
        cx=que[h];
        for(int i=1;cx;i++)
        {
            tcx=cx%10;//tcx为cx的倒数第i位 
            for(int j=1;j<=k;j++)
                if(tcx==gz[j][0])
                {
                    tx=f(que[h],i,gz[j][1]);
                    if(!p[tx])que[++t]=tx,p[tx]=1,ans++;
                }
            cx/=10;
        }
        h++;
    }
    return;
}
int main(){
    cin>>n>>k;
    for(int i=1;i<=k;i++)cin>>gz[i][0]>>gz[i][1];
    p[n]=1;
    bfs(n);
    cout<<ans<<endl;
//    for(int i=1;i<10000;i++)
//        if(p[i])cout<<i<<' ';
    return 0;
}
点击查看AC代码

1362:家庭问题(family)

#include<bits/stdc++.h>
using namespace std;
int a[101][101],p[101],gp,mx=1,cy,n;//gp家庭个数,cy家庭人数,mx最大家庭人数 
void dfs(int x)
{
    p[x]=1;
    for(int k=1;k<=n;k++)
        if(a[x][k]&&p[k]==0)
        {
            dfs(k);
            cy++;
            if(mx<=cy)mx=cy;
        }
    
}
int main()
{    
    int m,r,c;
    cin>>n>>m;
    for(int i=1;i<=m;i++)
    {
        cin>>r>>c;
        a[r][c]=a[c][r]=1;
    }
    for(int i=1;i<=n;i++)
        if(p[i]==0)
        {
            gp++;
            cy=1;
            dfs(i);
        }
    cout<<gp<<' '<<mx;
    return 0;
}
点击查看AC代码

1418:猴子选大王

第三章 树

第一节 二叉树

1336:【例3-1】找树根和孩子

//1336:【例3-1】找树根和孩子 
#include<iostream>
using namespace std;
int mt[101]; 
//mt[x][0]记录x的儿子结点数,mt[x][1...]依次记录x的儿子结点 
int n,m,x,y,maxx,maxn,num;
int main(){
    cin>>n>>m;
    for(int i=1;i<=m;i++)
    {
        cin>>x>>y;
        mt[y]=x; 
    }
    for(int i=1;i<=n;i++)
        if(!mt[i])
        {
            cout<<i<<endl;
            break;
        }
    for(int i=1;i<=n;i++)
    {
        num=0;
        for(int j=1;j<=n;j++)
        {
            if(mt[j]==i)num++;
            if(maxn<num)maxn=num,maxx=i;
        }
    }
    cout<<maxx<<endl;
    for(int i=1;i<=n;i++)
        if(mt[i]==maxx)cout<<i<<' ';
    return 0;
}
点击查看AC代码

1337:【例3-2】单词查找树

#include<bits/stdc++.h>
using namespace std;
string a[32770];
int main()
{
    int n=0;
    while(cin>>a[++n]);//输入
 
    n--;
 
    sort(a+1,a+n+1);
    int t=a[1].length();
 
    for(int i=2;i<=n;i++)
    {
        int j=0;
        while(a[i][j]==a[i-1][j]&&j<a[i-1].length())j++;
        t+=a[i].length()-j;
    }
    cout<<t+1<<endl;
    return 0;
}
点击查看AC代码

1338:【例3-3】医院设置

//1338:【例3-3】医院设置
#include<iostream>
#include<cstring>
using namespace std;
int a[101],p[101],t[101][101],x,l,r,n,minn,ans,sum;
int main(){
    memset(t,1,sizeof(t));
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>a[i]>>l>>r;
        p[l]=p[r]=i;
        t[i][i]=0;
        if(l)t[i][l]=t[l][i]=1;
        if(r)t[i][r]=t[r][i]=1;
    }
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            for(int k=1;k<=n;k++)
                if(t[i][j]>t[i][k]+t[k][j])
                    t[i][j]=t[i][k]+t[k][j];
    for(int i=1;i<=n;i++)
    {
        sum=0;
        for(int j=1;j<=n;j++)
            sum+=t[i][j]*a[j];
        if(minn>sum||!minn)minn=sum,ans=i;
    }
    //cout<<ans<<endl;
    cout<<minn;
    return 0;
}
点击查看AC代码
//1338:【例3-3】医院设置(结构)
#include<iostream>
using namespace std;
struct hp{
    int num;
    int no;
    hp *pa; 
}tree[101],*p;
int n,l,r,a[101],f[101][101],sum,minn=1e7;
int main(){
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>tree[i].num>>l>>r;
        tree[i].no=i;
        if(l)tree[l].pa=&tree[i];
        if(r)tree[r].pa=&tree[i];
    }
    for(int i=2;i<=n;i++)
    {
        l=0;
        tree[1].pa=NULL; 
        p=&tree[i];
        while(1)
        {
            a[++l]=p->pa->no;//a[1...l]存储到根节点的路径 
            if(a[l]==1)break;
            else p=p->pa;
        }
        f[1][i]=f[i][1]=l;
        for(int j=2;j<=n;j++)
        {
            if(i==j)continue;
            r=0;
            p=&tree[j];
            int g=1;
            while(g)
            {
                for(int k=1;k<=l;k++)
                    if(p->no==a[k])//a[k]就是i结点和j结点的最早公共祖先 
                    {
                        f[i][j]=f[j][i]=k+r;
                        g=0;
                        break;
                    }
                p=p->pa;
                r++;
            }
        }    
    }
    for(int i=1;i<=n;i++)//穷举医院位置,擂台求最小值 
    {
        sum=0;
        for(int j=1;j<=n;j++)
            sum+=f[i][j]*tree[j].num;
        if(minn>sum||!minn)minn=sum;
    }
    cout<<minn;
    return 0;
}
点击查看AC代码

1339:【例3-4】求后序遍历

//1339:【例3-4】求后序遍历
#include<iostream>
using namespace std;
string s1,s2;
int mf(string,char);
void hx(int,int,int,int);
int main(){
    cin>>s1>>s2;
    int le=s1.size();
    hx(0,le-1,0,le-1);
    return 0;
}
int mf(string x,char ch)
{
    int len=x.size();
    for(int i=0;i<len;i++)
        if(x[i]==ch)return i;
    return -1;
}
void hx(int b1,int e1,int b2,int e2)
{
    int wz=mf(s2,s1[b1]);
    if(wz>b2)hx(b1+1,b1+wz-b2,b2,wz-1);
    if(wz<e2)hx(b1+wz-b2+1,e1,wz+1,e2);
    cout<<s1[b1];
}
点击查看AC代码

1340:【例3-5】扩展二叉树

//1340:【例3-5】扩展二叉树
#include<bits/stdc++.h>
using namespace std;
struct node
{
    char data;
    node *l,*r;
};
char ch;
node* creat(node *p)
{
    ch=getchar();
    if(ch=='.') p=NULL;
    else
    {
        p->data=ch;
        p->l=creat(new node);
        p->r=creat(new node);
    }
    return p;
}
void przx(node *p)
{
    if(p!=NULL)
    {
        przx(p->l);
        cout<<p->data;
        przx(p->r);
    }
    return ;
}
void prhx(node *p)
{
    if(p!=NULL)
    {
          prhx(p->l);
         prhx(p->r);
          cout<<p->data;
    }
    return ;
}
int main()
{
    node *q,n;
    q=&n;
    q=creat(q);
    przx(q);
    cout<<endl;
    prhx(q);
    return 0;
}
点击查看AC代码

1363:小球(drop)

//1363:小球(drop)
#include<iostream>
using namespace std;
int const n=1<<20+1;
bool tree[n]; 
int d,l,ans;
int main(){
    cin>>d>>l;
    for(int i=1;i<=l;i++)
    {
        ans=1;
        for(int j=1;j<d;j++)
        {
            if(tree[ans])
            {
                tree[ans]=false;
                ans=ans*2+1;                
            }
            else
            {
                tree[ans]=true;
                ans=ans*2;                
            }    
        }
    }
    cout<<ans;
    return 0;
}
点击查看AC代码

1364:二叉树遍历(flist)

//1364:二叉树遍历(flist)
#include<iostream>
#include<cstdio>
using namespace std;
string s1,s2;
int ba[255],ab[255];
void calc(int l,int r)
{
    if(l>r)return;
    int dw,maxx=300;
    for(int i=l;i<=r;i++)
        if(maxx>ab[i])maxx=ab[i];
    cout<<s2[maxx];
    dw=ba[maxx];
    calc(l,dw-1);
    calc(dw+1,r);
}
int main(){
    cin>>s1>>s2;
    int len=s1.size()-1;
    for(int i=0;i<=len;i++)
        for(int j=0;j<=len;j++)
            if(s1[i]==s2[j])ab[i]=j,ba[j]=i;
    calc(0,len);
    return 0;
}
点击查看AC代码

1365:FBI树(fbi)

#include<iostream>
#include<cstdio>
using namespace std;
int c[10];
struct node
{
    char ch;
    node *l,*r;
};
node tree[10000];
int n,t,a,b;
string s;
char t1,t2;
void pr( node *p)
{
    if(p)
    {
        pr(p->l);
        pr(p->r);
        cout<<p->ch;
    }
}
int main(){
    cin>>n>>s;
    c[0]=1;
    for(int i=1;i<=n+1;i++)c[i]=c[i-1]*2;
    for(int i=c[n];i<c[n+1];i++)
        tree[i].ch=s[i-c[n]]=='1'?'I':'B';
    for(int i=c[n]-1;i>=1;i--)
    {            
        tree[i].l=&tree[i*2];
        tree[i].r=&tree[i*2+1];
        t1=tree[i].l->ch;
        t2=tree[i].r->ch;
        if(t1!=t2||t1=='F'&&t2=='F')tree[i].ch='F';
        else if(t1==t2&&t1=='B')tree[i].ch='B';
        else tree[i].ch='I';
    }
//    for(int i=1;i<c[n+1];i++)
//    cout<<i<<':'<<tree[i].ch<<endl;
    pr(&tree[1]);
    return 0;
}
点击查看AC代码

1366:二叉树输出(btout)

//1366:二叉树输出(btout)
#include<iostream>
#include<cstdio>
using namespace std;
string s1,s2;
int a[256],b[256],c[256],n;
struct node
{
    int no,tot;
    char va;
    node *l,*r;
};
node tree[256],*p;
void build(int x1,int y1,int x2,int y2)
{
    if(x1==y1)return;
    int wz=a[x1];
    if(wz>x2)
    {
        tree[x1].l=&tree[x1+1];
        build(x1+1,x1+wz-x2,x2,wz-1);
    }
    if(x1+wz-x2<y1)
    {
        tree[x1].r=&tree[x1+wz-x2+1];
        build(x1+wz-x2+1,y1,wz+1,y2);
    }
}
int calc(node *q)
{
    q->tot=0;
    if(q->l)q->tot+=calc(q->l);
    if(q->r)q->tot+=calc(q->r);
    if(!q->tot)q->tot=1;
    return q->tot;
}
void pr(node *q)
{
    if(q)
    {
        for(int i=0;i<q->tot;i++)
            cout<<q->va;
        cout<<endl;
        pr(q->l);
        pr(q->r);
    }
}
int main(){
    cin>>s1>>s2;
    n=s1.size();
    for(int i=0;i<n;i++)
        tree[i].va=s1[i],tree[i].no=i;
    for(int i=0;i<n;i++)
        for(int j=0;j<n;j++)
            if(s1[i]==s2[j])
                a[i]=j,b[j]=i;
    node *q=&tree[0];
    build(0,n-1,0,n-1);
    calc(q);
    pr(tree);
    return 0;
}
点击查看AC代码

1367:查找二叉树(tree_a)

//1367:查找二叉树(tree_a)
#include<iostream>
using namespace std;
struct node
{
    int num;
    node *l,*r;
};
node tree[101];
int n,x,l,r,ans;
void pr(node *p)
{
    if(p)
    {
        pr(p->l);
        ans++;
        if(p->num==x)
        {
            cout<<ans;
            return;    
        }
        pr(p->r);
    }
}
int main(){
    cin>>n>>x;
    for(int i=1;i<=n;i++)
    {
        cin>>tree[i].num>>l>>r;
        if(l)tree[i].l=&tree[l];
        if(r)tree[i].r=&tree[r];
    }
    pr(&tree[1]);
    return 0;
}
点击查看AC代码

1368:对称二叉树(tree_c)

//1368:对称二叉树(tree_c)
#include<iostream>
#include<cstdio>
using namespace std;
string s;
int n,ans;
int main(){
    cin>>s;
    n=s.size();
    ans=(n+1)%2;
    for(int i=1;i<n-1;i+=2)
    {
        if(ans)break;
        ans=(s[i]=='#')^(s[i+1]=='#');     
    }
    if(ans)cout<<"No";
    else cout<<"Yes";
    return 0;
}
点击查看AC代码

第二节 堆及其应用

1369:合并果子(fruit)

#include<bits/stdc++.h>
using namespace std;
priority_queue<int,vector<int>,greater<int> >a;
int main()
{
    int n,tmp;
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>tmp;
        a.push(tmp);
    }
    int ans=0;
    while(!a.empty())
    {
        int s1=a.top();
        a.pop();
        if(a.empty())break;
        else
        {
            int s2=a.top();
            a.pop();
            ans+=s1+s2;
            a.push(s1+s2);
        }
    }
    cout<<ans;
    return 0;
}
点击查看AC代码

1370:最小函数值(minval)

#include<bits/stdc++.h>
using namespace std;
priority_queue<int,vector<int>,less<int> >q;
priority_queue<int,vector<int>,greater<int> >w;
int main()
{
    int n,m,a,b,c,tmp,maxx;
    cin>>n>>m;
    cin>>a>>b>>c;
    for(int j=1;j<=m;j++)
    {
        tmp=a*j*j+b*j+c;
        q.push(tmp);
    }
    for(int i=1;i<n;i++)
    {
        cin>>a>>b>>c;
        maxx=q.top();
        for(int k=1;k<=m;k++)
        {
            int heap=a*k*k+b*k+c;
            if(heap<maxx)
            {
                q.pop();
                q.push(heap);
                maxx=q.top();
            }
            else break;
        }
    }
    for(int i=1;i<=m;i++)
    {
        int tr=q.top();
        q.pop();
        w.push(tr);
    }
    for(int i=1;i<=m;i++)
    {
        int dd=w.top();
        w.pop();
        cout<<dd<<" ";
    }
    return 0;
}
点击查看AC代码

1371:看病

//1371:看病
#include<iostream>
#include<cstdio>
using namespace std;
struct node{
    char name[25];
    int num;
}heap[100001],tmp;
char zl[5];
int n,hs;
void put(node d)
{
    int now=++hs,next;
    heap[hs]=d;
    while(now>1)
    {
        next=now>>1;
        if(heap[now].num<=heap[next].num)return;
        swap(heap[now],heap[next]);
        now=next;
    }
    return;
}
void get()
{
    if(hs)printf("%s %d\n",heap[1].name,heap[1].num);
    else 
    {
        printf("none\n");
        return;
    }
    int now=1,next=2;
    heap[1]=heap[hs--];
    while(next<=hs)
    {
        if(next<hs&&heap[next].num<heap[next+1].num)next++;
        if(heap[next].num<heap[now].num)break;
        swap(heap[next],heap[now]);
        now=next;
        next=now<<1;
    }
}
int main(){
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        scanf("%s",zl);
        if(zl[1]=='o')get();
        else
        {
            scanf("%s %d",&tmp.name,&tmp.num);
            put(tmp);
        }
    }
    return 0;
}
点击查看AC代码

1372:小明的账单

//1372:小明的账单 
#include<iostream>
#include<set>
#include<cstdio>
using namespace std;
int n,m,x; 
multiset<int> zd;
int main()
{
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        scanf("%d",&m);
        for(int j=1;j<=m;j++)
        {
            scanf("%d",&x);
            zd.insert(x);
        }
        printf("%d %d\n",*zd.begin(),*(--zd.end()));
        zd.erase(zd.begin());        
        zd.erase(--zd.end());
    }
     return 0;
}
点击查看AC代码

1373:鱼塘钓鱼(fishing)

#include<bits/stdc++.h>
#define fish first
#define lake second
using namespace std;
priority_queue<pair<int,int> >heap;
int f[105];
int t[105];
int d[105];
int main()
{    int n;    
     cin>>n;    
     for(int i=1;i<=n;i++) 
     cin>>f[i];    
     for(int i=1;i<=n;i++) 
     cin>>d[i];    
     for(int i=1;i<n;i++)  
     cin>>t[i];    
     int m;    
     cin>>m;    
     int T=0;    
     int t1=0;   
     int ans=0;    
     int maxn=0;    
     for(int k=1;k<=n;k++){//枚举最远走到的池塘的编号        
     T=m-t1;//计算剩余的时间        
     ans=0;        
     while(!heap.empty())
     {            
     heap.pop();       
     }        
     for(int i=1;i<=k;i++)
     {//收集能够钓鱼的池塘治疗            
     heap.push(make_pair(f[i],i));        
     }        
     while(T>0&&heap.top().fish>0)
     {      pair<int ,int >a=heap.top();            
            heap.pop();            
            ans+=a.fish;//贪心取鱼最多的池塘            
            a.fish-=d[a.lake];//修改鱼的数量           
             heap.push(a);//维护堆            
             T--;//剩余时间变少       
     }        
     if(ans>maxn) 
     maxn=ans;//刷新最优解        
     t1+=t[k];//累计走路需要的时间    
     }    
     cout<<maxn<<endl;    
    return 0;
}
点击查看AC代码

第四章 图论算法

第一节 图的遍历

1341:【例题】一笔画问题

//1341:【例题】一笔画问题
#include<bits/stdc++.h>
using namespace std;
int mapp[1005][1005];
int n,m;
int s[105];
int c=0;
int num[2005];
void dfs(int i)
{
    for(int j=1; j<=n; j++)
    {   if(mapp[i][j]==1) {
            mapp[i][j]=mapp[j][i]=0;
            dfs(j);
        }
    }
    num[++c]=i;
}
int main() {
    memset(mapp,0,sizeof(mapp));
    cin>>n>>m;
    int a,b;
    for(int i=1; i<=m; i++) {
        cin>>a>>b;
        mapp[a][b]=mapp[b][a]=1;
        s[a]++;
        s[b]++;
    }
    int flag=1;
    for(int i=1; i<=n; i++) {
        if(s[i]%2==1) {
            flag=i;
        }
    }
    dfs(flag);
    for(int i=1; i<=c; i++) {
        cout<<num[i]<<" ";
    }
    cout<<endl;
    return 0;
}
点击查看AC代码

1374:铲雪车(snow)

//铲雪车 
#include<iostream>
#include<cmath>
using namespace std;
int main()
{
    long long int sx,sy,x1,y1,x2,y2;
    double s=0;
    cin>>sx>>sy;
    while(cin>>x1>>y1>>x2>>y2)
    {        
        s+=sqrt((x1-x2)*(x1-x2)+(y1-y2)*(y1-y2)); 
    }
    long long int h=s/10000;
    long long int f=(s/10000-h)*60+0.5;
    cout<<h<<':';
    if(f<10)cout<<'0';
    cout<<f<<endl;
    return 0;
}
点击查看AC代码

1375:骑马修栅栏(fence)

#include<bits/stdc++.h>
using namespace std;
int n;
int maxn;
int beginn=10000;
int mapp[1000][1000];
int path[1000];
int d[1000];
int start=0;
int cnt=0;
void dfs(int i)
{
    for(int j=beginn;j<=maxn;j++){
        if(mapp[i][j]){
            mapp[i][j]--;
            mapp[j][i]--;
            dfs(j);
        }
    }
    path[++cnt]=i;
}
int main()
{
    ios::sync_with_stdio(false);
    cin>>n;
    for(int i=0;i<n;i++){
        int x,y;
        cin>>x>>y;
        mapp[x][y]++;//说明x和y有连边,这里++是因为俩个点之间可以不止一个栅栏
        mapp[y][x]++;
        d[x]++;//统计每点的度
        d[y]++;
        beginn=min(min(x,y),beginn);//这个是找到最小的点
        maxn=max(max(x,y),maxn);//这个是找点
    }
 
 
    for(int i=beginn;i<=maxn;i++){//注意这是从点的的度来找的,找奇点
        if(d[i]%2){
            start=i;
            break;
        }
    }
 
    if(start==0) start=beginn;//如果没有找到奇点那么就从最小的点开始遍历
 
    dfs(start);
 
    for(int i=cnt;i>=1;i--){
        cout<<path[i]<<endl;
    }
 
    return 0;
}
点击查看AC代码

第二节 最短路径算法

1342:【例4-1】最短路径问题

//1342:【例4-1】最短路径问题 
//dijkstra算法 
#include<iostream>
#include<cstring>
#include<iomanip>
#include<cmath>
using namespace std;
const int maxx=0x7fffffff;
int n,m,p[101][2],l[101][101],que[301];
double  d[101],f[101][101],ans;
bool q[101];
int main()
{
    int a,b,x,y,s,e;
    double minx=maxx;
    cin>>n;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            f[i][j]=maxx;
    for(int i=1;i<=n;i++)
    {
        f[i][i]=0;
        d[i]=0x7fffffff;
        q[i]=false;
        cin>>p[i][0]>>p[i][1];
    }
    
    cin>>m;
    for(int i=1;i<=m;i++)
    {
        cin>>a>>b;
        x=p[a][0]-p[b][0];
        y=p[a][1]-p[b][1];
        f[b][a]=f[a][b]=sqrt(x*x+y*y);
        l[a][0]++,l[b][0]++;
        l[a][l[a][0]]=b,l[b][l[b][0]]=a;
    }
    cin>>s>>e;
    
    d[s]=0;    
    int head=1,tail=1,tx,cx;
    que[1]=s; 
    while(head<=tail)
    {
        cx=que[head++];
        q[cx]=false;
        for(int i=1;i<=l[cx][0];i++)
        {
            tx=l[cx][i];
            //cout<<"cx:"<<cx<<'-'<<tx<<' '<<f[tx][cx]<<endl;
            if(d[tx]>d[cx]+f[tx][cx])
            {
                d[tx]=d[cx]+f[tx][cx];
                if(!q[tx])que[++tail]=tx,q[tx]=true;
            }
        }
    }
    ans=d[e];
    cout<<fixed<<setprecision(2)<<ans<<endl;
    return 0;
}
点击查看AC代码

1343:【例4-2】牛的旅行

//1343:【例4-2】牛的旅行
#include<iostream>
#include<cmath>
#include<iomanip>
using namespace std;
const int maxn=0x3fffffff;
const int N=151;
int pt[N][2],n;
double s[N][N],f[N][N],d[N],ans;
/*pt数组存储点的坐标,s数组存储任两点间的距离
f数组存储任两点间的最短路径长,d数组存储到某点的最大路径长
(若两点不相连通则该值为0)*/
int main()
{
    int x,y;
    char tx;
    cin>>n;
    //输入点的坐标 
    for(int i=1;i<=n;i++)cin>>pt[i][0]>>pt[i][1];
    //输入邻接表 
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
        {
            cin>>tx;
            x=pt[i][0]-pt[j][0];
            y=pt[i][1]-pt[j][1];
            s[j][i]=s[i][j]=sqrt(x*x+y*y);
            //若两点连通则路径长等于两点间距离,否则无穷大 
            if(tx=='1'||i==j)f[i][j]=f[j][i]=s[i][j];    
            else f[i][j]=f[j][i]=maxn;
        }
    //弗洛伊德法求两点间的最小路径长 
    for(int k=1;k<=n;k++)
        for(int i=1;i<=n;i++)
            for(int j=1;j<=n;j++)
                if(f[i][j]>f[i][k]+f[j][k])
                    f[i][j]=f[i][k]+f[j][k];
    //求与i点连通的点到i点的最大距离d[i] 
    for(int i=1;i<=n;i++)d[i]=0;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            if(f[i][j]<maxn-1&&d[i]<f[i][j])d[i]=f[i][j];
    //f[i][j]>maxn-1意味着i,j两个点位于两个不同牧场
    //如果连通ij合成一个大的牧场,新牧场直径为 d[i]+d[j]+s[i][j]
    ans=maxn;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            if(f[i][j]>maxn-1&&ans>d[i]+d[j]+s[i][j])
                ans=d[i]+d[j]+s[i][j];
    //新牧场直径不可能比原来牧场直径小
    for(int i=1;i<=n;i++)if(d[i]>ans)ans=d[i]; 
    cout<<fixed<<setprecision(6)<<ans<<endl;
    return 0;
}
点击查看AC代码

1344:【例4-4】最小花费

//1344:【例4-4】最小花费
#include<iostream>
#include<cmath>
#include<iomanip>
using namespace std;
const int maxn=0x3fffffff;
const int N=2001;
int n,m,d[N],msg[N][N],p[N];
double ss[N],f[N][N];
double ans;
/*dijkstra算法*/
int main()
{
    int a,b,c,s,e,tmp;
    double maxx;
    cin>>n>>m;
    //处理任两人间转账实收比例 
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            f[i][j]=f[j][i]=0;
    for(int i=1;i<=m;i++)
    {
        cin>>a>>b>>c;
        f[a][b]=f[b][a]=1-c/100.0;
        msg[a][0]++,msg[b][0]++;
        msg[a][msg[a][0]]=b,msg[b][msg[b][0]]=a;
    }
    cin>>s>>e;
    //弗洛伊德法求两人间最大实收比例 
//    for(int k=1;k<=n;k++)
//        for(int i=1;i<=n;i++)
//            for(int j=1;j<=n;j++)
//                if(f[i][j]<f[i][k]*f[j][k])
//                    f[i][j]=f[i][k]*f[j][k];
    for(int i=1;i<=n;i++)ss[i]=f[s][i];
        
    ss[s]=1;
    p[s]=1;
    while(1)
    {
        tmp=0;
        maxx=0;
        for(int i=1;i<=n;i++)
            if(p[i]==0&&maxx<ss[i])
                maxx=ss[i],tmp=i;
        if(tmp==0)break;
        p[tmp]=1;
        for(int i=1;i<=msg[tmp][0];i++)
        {
            int tt=msg[tmp][i];
            if(ss[tt]<ss[tmp]*f[tt][tmp])ss[tt]=ss[tmp]*f[tt][tmp];
        }
    }
    ans=100/ss[e];
    cout<<fixed<<setprecision(8)<<ans<<endl;
    return 0;
}
点击查看AC代码

1345:【例4-6】香甜的黄油

//1345:【例4-6】香甜的黄油 
#include<iostream>
#include<cstring> //memset须用 
using namespace std;
const int N=2001; 
int p[N],f[N],d[N][N],msg[N][N],ans,tot=0x7fffffff,c,n,m;
int bz[N],que[N*2],h,t=1;
int main()
{
    int x,y,s;
    memset(d,0x3f,sizeof(d));
    cin>>c>>n>>m;
    for(int i=1;i<=c;i++)cin>>p[i]; 
    for(int i=1;i<=m;i++)
    {
        cin>>x>>y>>s;
        d[i][i]=0;
        d[x][y]=d[y][x]=s;
        msg[x][++msg[x][0]]=y;
        msg[y][++msg[y][0]]=x;
    }
//    for(int k=1;k<=n;k++)//弗洛伊德求最小距离 (超时) 
//        for(int i=1;i<=n;i++)
//            for(int j=1;j<=n;j++)
//                if(d[i][j]>d[i][k]+d[j][k])d[i][j]=d[i][k]+d[j][k];

        //以下采用SPFA算法求到i牧场的最小距离
        //f[j]为i,j两牧场的最小距离 ,bz[j]标识j是否在队列中 
    for(int i=1;i<=n;i++)//暴力枚举放置点 
    {
        for(int j=1;j<=n;j++)f[j]=0x3fffffff,bz[j]=0;
        f[i]=0,t=1,h=0,que[1]=i;
        do
        {
            h=h%1601+1;//采用循环队列 
            x=que[h],bz[x]=0;
            for(int j=1;j<=msg[x][0];j++)
            {
                s=msg[x][j];
                if(f[s]>f[x]+d[x][s])
                {
                    f[s]=f[x]+d[x][s];
                    if(bz[s]==0)
                    {
                        t=t%1601+1;
                        que[t]=s,bz[s]=1;
                     } 
                }
            }
        }while(h!=t);
        s=0;
        for(int j=1;j<=c;j++)s+=f[p[j]];
        if(tot>s)tot=s;
    } 
//      for(int i=1;i<=n;i++)
//      {
//        for(int j=1;j<=n;j++)
//            cout<<d[i][j]<<' ';
//        cout<<p[i]<<endl;
//      }
    cout<<tot<<endl;
    return 0;
}
点击查看AC代码

1376:信使(msner)

//1376:信使(msner) 
#include<iostream>
using namespace std;
const int maxn=1e8; 
const int N=101;
int d[N][N],ms[N][N],p[N],f[N],n,m,ans;
int main()
{
    ios::sync_with_stdio(0);
    int x,y,s;
    cin>>n>>m;
    for(int i=1;i<=n;i++)p[i]=0,f[i]=maxn;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            d[i][j]=maxn;
    for(int i=1;i<=m;i++)
    {
        cin>>x>>y>>s;
        ms[x][++ms[x][0]]=y;
        ms[y][++ms[y][0]]=x;
        d[x][y]=d[y][x]=s;
     } 
     for(int i=1;i<=ms[1][0];i++)f[ms[1][i]]=d[1][ms[1][i]];
     f[1]=0,p[1]=1;
     for(int i=1;i<n;i++)
     {
         s=0;
         x=maxn;
         for(int j=2;j<=n;j++)
         {
             if(p[j]==0&&f[j]<x)
             {
                 x=f[j];
                 s=j;
             }
        } 
        if(s==0)break;
        p[s]=1;
        for(int j=1;j<=ms[s][0];j++)
        {
            y=ms[s][j];
            if(p[y]==0&&f[y]>f[s]+d[s][y])f[y]=f[s]+d[s][y];
        }
     }
     ans=0;
     for(int i=2;i<=n;i++)
         if(ans<f[i])ans=f[i];
    if(ans==maxn)ans=-1;
    cout<<ans<<endl;
    return 0;
}
点击查看AC代码

1377:最优乘车(travel)

//1377:最优乘车(travel) 
#include<iostream>
#include<cstdio>
using namespace std;
const int N=501;
const int maxn=1e9;
string str;
int link[N][N],msg[N][N],dis[N],p[N],n,m,cnt,x;
int main()
{
    //ios::sync_with_stdio(0);
    cin>>m>>n;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            if(i==j)link[i][i]=0;
            else link[i][j]=maxn;
        
    for(int i=1;i<=m;i++)
    {        
        cnt=0,x=0;
        char ch='\0';    
        while(ch<'0'||ch>'9')ch=getchar();
        do
        {    
            if(ch>='0'&&ch<='9')x=x*10+ch-'0';
            if(ch=='\n'||ch==' ')
            {
                if(x)p[++cnt]=x,x=0;
                if(ch=='\n')break;
            }
            ch=getchar();
        }while(1);
        for(int j=1;j<cnt;j++)//同一线路前面站到后面站就一次搞定 
        {
            int x=p[j];
            for(int k=j+1;k<=cnt;k++)
            {
                int y=p[k];
                msg[x][++msg[x][0]]=y,link[x][y]=1;    //此处非双向 
            }
        }
            
    }
    for(int k=1;k<=n;k++)//弗洛伊德求最小距离 
        for(int i=1;i<=n;i++)
            for(int j=1;j<=n;j++)
                if(link[i][j]>link[i][k]+link[k][j])
                    link[i][j]=link[i][k]+link[k][j];
    
    //SPFA算法求最小距离 
//    for(int i=2;i<=n;i++)dis[i]=link[1][i],p[i]=0;
//    dis[1]=0,p[1]=1; 
//    for(int i=1;i<=n;i++)
//    {
//        x=maxn;
//        cnt=0;
//        for(int j=2;j<=n;j++)
//            if(p[j]==0&&x>dis[j])
//                x=dis[j],cnt=j;
//        if(cnt==0)break;
//        p[cnt]=1;
//        for(int j=1;j<=msg[cnt][0];j++)
//        {
//            x=msg[cnt][j];
//            if(dis[x]>link[cnt][x]+dis[cnt])
//                dis[x]=link[cnt][x]+dis[cnt];
//        }
//    }
//    for(int i=1;i<=n;i++)
//    {
//        for(int j=1;j<=n;j++)
//            cout<<link[i][j]<<' ';
//        cout<<dis[i]<<endl;
//    }
//    if(dis[n]!=maxn)cout<<dis[n]-1<<endl;
//    else cout<<"N0\n";
    if(link[1][n]==maxn)cout<<"NO\n";
    else cout<<link[1][n]-1<<endl;
    return 0;
}
点击查看AC代码

1378:最短路径(shopth)

//1378:最短路径(shopth)
#include<iostream>
#include<cstdio>
using namespace std;
const int N=81;
const int inf=1e9;
int link[N][N],msg[N][N],dis[N],p[N],n,s;
//msg[x][y]存储以x为起点的边信息,msg[x][0]存储边的条数,其后依次存储各边终点 
int que[N*2+3],h=0,t=1,cx,tx;
int read()
{
    int x=0,f=1,cnt=0;
    //cnt记录输入的数字个数,若为0则说明只输入了一个-(无边) 
    char ch='\0';
    while(ch!='-'&&(ch<'0'||ch>'9'))ch=getchar();
    do
    {
        if(ch=='-')f=-1;
        else cnt++,x=x*10+ch-'0';
        ch=getchar();
    }while(ch>='0'&&ch<='9');
    if(cnt==0)x=inf;
    else x*=f;
    return x;
}
int get(string s0)
{
    if(s0=="-")return inf;
    int f=1,x=0;
    for(int i=0;i<s0.length() ;i++)
    {
        if(s0[i]=='-')f=-1;
        else x=x*10+s0[i]-'0';
    }
    return x*f;
}
int main()
{
    //ios::sync_with_stdio(0);
    cin>>n>>s;
    string ss;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
        {
            cx=read();
            //cin>>ss;            
            link[i][j]=cx;
            if(i!=j&&cx<inf)msg[i][++msg[i][0]]=j;
        }
    //因为有负权边,不可用dijkstra,故采用SPFA 
    for(int j=1;j<=n;j++)dis[j]=inf,p[j]=0;
    dis[s]=0,h=0,t=1,que[1]=s;
    while(h!=t)//队列中最多n个元素,不可能队满,h=t则说明队空 
    {
        h=h%(N*2)+1;//用循环队列 
        cx=que[h],p[cx]=0;
        for(int j=1;j<=msg[cx][0];j++)
        {
            tx=msg[cx][j];
            if(dis[tx]>dis[cx]+link[cx][tx])//tx的值因cx而更新 
            {
                dis[tx]=dis[cx]+link[cx][tx];//更新tx的值 
                if(p[tx]==0)//如果tx没在队列中则让tx入队 
                    t=t%(N*2)+1,que[t]=tx,p[tx]=1;
            }
        }
    }
//    for(int k=1;k<=n;k++)
//        for(int i=1;i<=n;i++)
//            for(int j=1;j<=n;j++)
//                if(link[i][j]>link[i][k]+link[k][j])
//                     link[i][j]=link[i][k]+link[k][j];
    for(int i=1;i<=n;i++) 
        if(i!=s)cout<<'('<<s<<" -> "<<i<<") = "<<dis[i]<<endl; 
    return 0;
}
点击查看AC代码

1379:热浪(heatwv)

//1379:热浪(heatwv) 
#include<iostream>
using namespace std;
int a[2501][2501],b[2501][2501],c[2501],p[2501];
int T,C,Ts,Te; 
void dfs(int x)
{
    if(x==Ts)return;
    int t;
    for(int i=1;i<=b[x][0];i++)
    {
        t=b[x][i];
        if(p[t])continue;
        if(c[x]+a[x][t]<c[t]||0==c[t])
        {
            c[t]=c[x]+a[x][t];
            p[t]=1;
            dfs(t);
            p[t]=0;
        }
    }
}
int main(){
    int Rs,Re,Ci,tmp;
    cin>>T>>C>>Ts>>Te;
    for(int i=1;i<=C;i++)
    {
        cin>>Rs>>Re>>Ci;
        if(a[Rs][Re]==0||a[Rs][Re]>Ci)
        {
            if(a[Rs][Re]==0)
            {
                b[Re][0]++;
                tmp=b[Re][0];
                b[Re][tmp]=Rs;
                b[Rs][0]++;
                tmp=b[Rs][0];
                b[Rs][tmp]=Re;
            } 
            a[Rs][Re]=a[Re][Rs]=Ci;            
        }            
    }
    p[Te]=1;
    dfs(Te);
    cout<<c[Ts]<<endl;
    return 0;
}
点击查看AC代码

1380:分糖果(candy)

//1380:分糖果(candy)
#include<bits/stdc++.h>
using namespace std;
const int N=1e5+1;
const int inf=1e9;
int link[N*200][2],last[N],dis[N],mk[N],que[N*2+2];
int ans,n,p,c,tt,x,y,cnt,h,t=1,cx,tx;
void init(int x,int y)
{
    link[++cnt][0]=last[x];
    link[cnt][1]=y;
    last[x]=cnt;
}
int main()
{
    ios::sync_with_stdio(0);
    cin>>n>>p>>c>>tt;
    for(int i=1;i<=p;i++)
    {
        cin>>x>>y;
        init(x,y);
        init(y,x);
    }
    for(int i=1;i<=n;i++)dis[i]=inf,mk[i]=0;
    dis[c]=0,que[1]=c;
    while(h!=t)
    {
        h=h%(N*2)+1;
        cx=que[h],mk[cx]=0;
        for(int i=last[cx];i;i=link[i][0])
        {
            tx=link[i][1];
            if(dis[tx]>dis[cx]+1)
            {
                dis[tx]=dis[cx]+1;
                if(mk[tx]==0)t=t%(N*2)+1,que[t]=tx,mk[tx]=1;
            }
        }
    }
    ans=0;
    for(int i=1;i<=n;i++)if(ans<dis[i])ans=dis[i];
    cout<<ans+tt+1<<endl; 
    return 0;
}
点击查看AC代码

1381:城市路(Dijkstra)

//1381:城市路(Dijkstra)
#include<iostream>
using namespace std;
const int inf=1e9;
const int N=2001;
int last[N],dis[N],mk[N],n,m,a,b,c,cnt,maxn,tx;
struct{
    int next,to,s;
}link[20005];
void init(int x,int y,int z)
{
    link[++cnt].next=last[x];
    link[cnt].to=y;
    link[cnt].s=z;
    last[x]=cnt;
}
int main()
{
    ios::sync_with_stdio(0);
    cin>>n>>m;
    for(int i=1;i<=m;i++)
    {
        cin>>a>>b>>c;
        init(a,b,c);
        init(b,a,c);
    }
    for(int i=2;i<=n;i++)dis[i]=inf,mk[i]=0;
    for(int i=1;i<n;i++)
    {
        maxn=inf,tx=0;
        for(int j=1;j<=n;j++)
            if(mk[j]==0&&maxn>dis[j])maxn=dis[j],tx=j;
        if(tx==0)break;
        mk[tx]=1;
        for(int j=last[tx];j;j=link[j].next)
        {
            int x=link[j].to;
            if(dis[x]>dis[tx]+link[j].s)
                dis[x]=dis[tx]+link[j].s;
        }
    }
    cout<<dis[n]<<endl;
    return 0;
}
点击查看AC代码

1382:最短路(Spfa)

//1382:最短路(Spfa) 
#include<iostream>
using namespace std;
const int N=1e5+1;
const int inf=1e9;
struct link{
    int pre,to,s;
}f[N*10]; 
int dis[N],mk[N],last[N],que[N*2+2],n,m,cnt;
void init(int x,int y,int z)
{
    cnt++;
    f[cnt].pre=last[x];
    f[cnt].to=y;
    f[cnt].s=z;
    last[x]=cnt;
}
int main()
{
    ios::sync_with_stdio(0);
    cin>>n>>m;
    int a,c,b;
    for(int i=1;i<=m;i++)
    {
        cin>>a>>b>>c;
        init(a,b,c);
        init(b,a,c);
    }
    int h=0,t=1,cx,tx;
    for(int i=1;i<=n;i++)dis[i]=inf,mk[i]=0;
    que[1]=1,dis[1]=0;
    while(h!=t)
    {
        h=h%(N*2)+1;
        cx=que[h],mk[cx]=0;
        for(int i=last[cx];i;i=f[i].pre)
        {
            tx=f[i].to;
            if(dis[tx]>dis[cx]+f[i].s)
            {
                 dis[tx]=dis[cx]+f[i].s; 
                 if(mk[tx]==0)
                     t=t%(N*2)+1,que[t]=tx,mk[tx]=1;
            }
        }
    }
    cout<<dis[n]<<endl;
    return 0;
}
点击查看AC代码

1419:SPFA(II)

//1419:SPFA(II)
#include<iostream>
using namespace std;
const int N=2e4+1;
const long long inf=1e16;
struct link{
    int pre,to,s;
}f[N*4]; 
long long dis[N];
int mk[N],last[N],que[N*2+2],n,m,cnt;
void init(int x,int y,int z)
{
    cnt++;
    f[cnt].pre=last[x];
    f[cnt].to=y;
    f[cnt].s=z;
    last[x]=cnt;
}
int main()
{
    ios::sync_with_stdio(0);
    cin>>n>>m;
    int a,c,b;
    for(int i=1;i<=m;i++)
    {
        cin>>a>>b>>c;
        init(a,b,c);
    }
    int h=0,t=1,cx,tx;
    for(int i=1;i<=n;i++)dis[i]=inf,mk[i]=0;
    que[1]=1,dis[1]=0;
    while(h!=t)
    {
        h=h%(N*2)+1;
        cx=que[h],mk[cx]=0;
        for(int i=last[cx];i;i=f[i].pre)
        {
            tx=f[i].to;
            if(dis[tx]>dis[cx]+f[i].s)
            {
                 dis[tx]=dis[cx]+f[i].s; 
                 if(mk[tx]==0)
                     t=t%(N*2)+1,que[t]=tx,mk[tx]=1;
            }
        }
    }
    cout<<dis[n]<<endl;
    return 0;
}
点击查看AC代码

1420:Dijkastra(II)

//1420:Dijkastra(II)
#include<iostream>
using namespace std;
const int N=2e5+1;
const long long inf=1e16;
struct link
{
    int pre,to,s;
}f[N*40];
long long dis[N],heap[N];
int n,m,a,b,c,cnt,last[N],pos[N],hp;
//int  mk[N],maxn,cx,tx;
//堆heap中存储占的编号,pos中存储点的在堆中位置 
void init(int x,int y,int z)
{
    f[++cnt].pre=last[x];
    f[cnt].to=y;
    f[cnt].s=z;
    last[x]=cnt;
}
void update(int x)//x为节点编号 
{
    int now=pos[x],next,a,b;//从now位置向上更新 
    while(now>1)
    {
        next=now>>1;//next为now的父节点 
        a=heap[now],b=heap[next];
        if(dis[a]>dis[b])break;
        heap[now]=b,heap[next]=a;//交换堆中两数的值 
        pos[a]=next,pos[b]=now;//同步更新两节点在堆中位置 
        now=next; 
    }
}
void put(int x)//x为节点编号 
{
    heap[++hp]=x;
    pos[x]=hp;
    update(x);
}
int get()
{
    int x=heap[1];
    heap[1]=heap[hp--];
    int now=1,next,a,b;//从now位置向下更新 
    while(now*2<=hp)
    {
        next=now<<1;//next为now的左子节点 
        if(next<hp&&dis[heap[next+1]]<dis[heap[next]])next++;
        //如果now的右子节点比左子节点还小,则右子节点更有可能成为新的父节点 
        a=heap[now],b=heap[next];
        if(dis[a]<dis[b])break;
        heap[now]=b,heap[next]=a;
        pos[a]=next,pos[b]=now;
        now=next; 
    }
    return x;
}
int main()
{
    ios::sync_with_stdio(0);
    cin>>n>>m;
    for(int i=1;i<=m;i++)
    {
        cin>>a>>b>>c;
        init(a,b,c);
        init(b,a,c);
    }
    dis[1]=0;
    for(int i=2;i<=n;i++)dis[i]=inf;
    put(1);
//    for(int i=last[1];i;i=f[i].pre )
//    {
//        tx=f[i].to;
//        if(dis[tx]>f[i].s)//可能有重边 
//            dis[tx]=f[i].s;
//    }
    while(hp)//hp为堆容量 
    {
        int x=get();
        pos[x]=0;//pos[x]=0表示x己出堆
        if(x==n)break;//n处于堆顶,n己变为白点,不会再更新
        for(int i=last[x];i;i=f[i].pre )
        {
            int y=f[i].to;
            if(dis[y]>dis[x]+f[i].s)
            {
                dis[y]=dis[x]+f[i].s;
                if(pos[y]==0)put(y);
                else update(y);//dis[y]的值变小,y在堆中位置只会向上走 
            }
        }             
    }
//    for(int i=1;i<n;i++)//普通dijkstra算法超时,须用堆优化 
//    {
//        maxn=inf,cx=0;
//        for(int j=2;j<=n;j++)
//            if(mk[j]==0&&maxn>dis[j])
//                maxn=dis[j],cx=j;
//        if(cx==0)break;
//        mk[cx]=1;
//        for(int j=last[cx];j;j=f[j].pre)
//        {
//            tx=f[j].to;
//            if(dis[tx]>dis[cx]+f[j].s)
//                dis[tx]=dis[cx]+f[j].s;
//        }
//    }
    cout<<dis[n]<<endl;    
    return 0;
}
点击查看AC代码

1421:Floyd

//1421:Floyd
#include<iostream>
using namespace std;
const int N=501;
const long long inf=1e16;
int n,m;
long long dis[N][N],s;
int main()
{
    ios::sync_with_stdio(0);
    long long a,b,c;
    cin>>n>>m;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            if(i==j)dis[i][j]=0;
            else dis[i][j]=inf;
    for(int i=1;i<=m;i++)
    {
        cin>>a>>b>>c;
        if(dis[a][b]>c)
            dis[a][b]=c;
    }
    for(int k=1;k<=n;k++)
        for(int i=1;i<=n;i++)
            for(int j=1;j<=n;j++)
                if(dis[i][j]>dis[i][k]+dis[k][j])
                //后面两条件若不加,则可以因为负权边把本不连通的边算成连通的边 
                    dis[i][j]=dis[i][k]+dis[k][j];
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            if(dis[i][j]>1e13)dis[i][j]=inf; 
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            s^=dis[i][j]+inf;
    cout<<s<<endl;
    return 0;
}
点击查看AC代码

第三节 图的连通性问题

1383:刻录光盘(cdrom)

//1383:刻录光盘(cdrom)
#include<iostream>
using namespace std;
const int N=201;
bool link[N][N];
int fa[N],n,ans,x;
int main()
{
    ios::sync_with_stdio(0);
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        fa[i]=i;
        cin>>x;
        while(x)
        {
            link[i][x]=true;
            cin>>x;
        }
    }
    for(int k=1;k<=n;k++)
        for(int i=1;i<=n;i++)
            for(int j=1;j<=n;j++)
                link[i][j]=link[i][j]||link[i][k]&&link[k][j];
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            if(link[i][j])fa[j]=fa[i];
    for(int i=1;i<=n;i++)if(fa[i]==i)ans++;
    cout<<ans<<endl;
    return 0;
}
点击查看AC代码

1384:珍珠(bead)

#include<iostream>
using namespace std;
const int N=100;
bool h[N][N],q[N][N];
int a[N],b[N],n,m,ans;
int main()
{
    ios::sync_with_stdio(0);
    int x,y;
    cin>>n>>m;
    for(int i=1;i<=m;i++)
    {
        cin>>x>>y;
        h[x][y]=q[y][x]=true;
    }
    for(int k=1;k<=n;k++)
        for(int i=1;i<=n;i++)
            for(int j=1;j<=n;j++)
            {
                h[i][j]=h[i][j]||h[i][k]&&h[k][j];
                q[i][j]=q[i][j]||q[i][k]&&q[k][j];    
            }
    for(int k=1;k<=n;k++)
        for(int i=1;i<=n;i++)
        {
            if(h[k][i])a[k]++;
            if(q[k][i])b[k]++;
        }
    for(int i=1;i<=n;i++)
        if(a[i]>=(n+1)/2||b[i]>=(n+1)/2)ans++;
    cout<<ans<<endl; 
    return 0;
}
点击查看AC代码

第四节 并查集

1346:【例4-7】亲戚(relation)

#include <iostream>
#include <cstdio>
using namespace std;
int n,m,f[200001];
int findx(int x)
{
    return f[x]==x?x:f[x]=findx(f[x]);
}
void uni(int x,int y)
{
    int r1=findx(x),r2=findx(y);
    if(r1!=r2)f[r2]=r1;
}
int main()
{
    int i,j,x,y;
    ios::sync_with_stdio(0);
    cin.tie(0);
    cin>>n>>m;
    //scanf("%d %d",&n,&m); 
    for(i=1; i<=n; i++) f[i]=i;
    for(i=1; i<=m; i++)
    {
      // scanf("%d%d",&x,&y);
         cin >> x >> y;
        uni(x,y);
    }
    cin>>m;
    for(i=1; i<=m; i++)
    {
     //  scanf("%d%d",&x,&y);
         cin >> x >> y;
        if(findx(x)==findx(y))
            //printf("Yes\n");
            cout<<"Yes\n";
        else //printf("No\n");
            cout<<"No\n"; 
    }
    return 0;
}
点击查看AC代码

1347:【例4-8】格子游戏

#include <iostream>
using namespace std;
struct node
{ int x,y;}f[301][301],k1,k2;
int i,j,m,n,x,y;
char c;
node root(node k)
{
  if((f[k.x][k.y].x==k.x)&&(f[k.x][k.y].y==k.y))return k;
  f[k.x][k.y]=root(f[k.x][k.y]);
  return f[k.x][k.y];
}
int main()
{
  cin>>n>>m;
  for(i=1;i<=n;i++)
     for(j=1;j<=n;j++)
       {f[i][j].x=i;f[i][j].y=j;}
  

for(i=1;i<=m;i++)
   {
     cin>>x>>y>>c;
     if(c=='D')
        {k1=root(f[x][y]);k2=root(f[x+1][y]);}
     if(c=='R')
        {k1=root(f[x][y]);k2=root(f[x][y+1]);}
     if((k1.x==k2.x)&&(k1.y==k2.y))
         {cout<<i<<endl;return 0;}
       else f[k1.x][k1.y]=k2;
    }
  cout<<"draw"<<endl;
  return 0;
}
点击查看AC代码

1385:团伙(group)

#include<bits/stdc++.h>
using namespace std;
int n,m;
int p[15000];
int vis[15000];
int findth(int x)
{    
      if(x==p[x]) return x;    
      return p[x]=findth(p[x]);
} 
void unionn(int x,int y)
{    int xx=findth(x);    
     int yy=findth(y);    
     if(xx!=yy) p[yy]=xx;
} 
 int main()
 {    
      scanf("%d %d",&n,&m);   
      for(int i=1;i<=2*n;i++) p[i]=i;    
      for(int i=1;i<=m;i++)
      {        int a,b,c;        
         scanf("%d %d %d",&a,&b,&c);        
         if(a==0) unionn(b,c);        
         if(a==1)
         {            
             unionn(b+n,c);           
              unionn(b,c+n);        
              
        }  
     }    
     int cnt=0;    
     for(int i=1;i<=n;i++)
     {        int t=findth(i);        
             if(!vis[t])
             {            vis[t]=1;            
                          cnt++;       
             } 
       }    
    printf("%d\n",cnt);  
  return 0;
  }
点击查看AC代码

1386:打击犯罪(black)

#include<cstdio>
#include<cstring>
#include<iostream>
#define max(a,b) (a)>(b)?(a):(b)
#define min(a,b) (a)<(b)?(a):(b)
using namespace std;
int n,xx,yy,k,a[1005][1005],dad[1005],b[1005];
int find(int dep){return dad[dep]==dep?dep:dad[dep]=find(dad[dep]);}//并查集
void lj(int x,int y)
{
    xx=find(x);
    yy=find(y);
    dad[min(xx,yy)]=max(xx,yy);//连接两个点
}
int main()
{
    scanf("%d",&n);
    for (int i=1;i<=n;++i)
      {
          scanf("%d",&a[i][0]);
          for (int j=1;j<=a[i][0];++j)
            scanf("%d",&a[i][j]);
      }
    for (int i=1;i<=n;++i)
      dad[i]=i;
    int i=n+1;
    while (!k)
      {
          i--;
          for (int j=1;j<=a[i][0];++j)
            if (a[i][j]>=i) lj(i,a[i][j]);//插入点
          memset(b,0,sizeof(b));
          for (int j=i;j<=n;++j)
            b[find(j)]++;//累加
          for (int j=i;j<=n;++j)
          {
              if (b[j]>n/2)//判断
                {
                    k=1;//不符合
                    break;
                }
          }
      }
    printf("%d",i);
}
点击查看AC代码

1387:搭配购买(buy)

//1387:搭配购买(buy) 
#include<cstdio>
#include<iostream>
using namespace std;
const int maxn = 10000+10;
int p[maxn],sumw[maxn],sumc[maxn];
// 分别记录每件云朵的祖先,每一种搭配的总金额,每一种搭配的总价值 
int w[maxn],c[maxn],f[maxn];
//分别记录每一个背包的总金额,总价值,可获得的总的最大价值 
int n,m,C;
 int find(int x)//采用压缩路径法找祖先 
 {
     return x==p[x]?x:p[x]=find(p[x]);
 } 
 int main() {
     scanf("%d%d%d",&n,&m,&C);
    for(int i=1;i<=n;i++) 
        scanf("%d%d",&sumw[i],&sumc[i]),p[i]=i;
    //并查集思路找代表元(祖先) 
     int u,v;
     for(int i=0;i<m;i++) {
         scanf("%d%d",&u,&v);
         int x=find(u),y=find(v);
         if(x!=y) {
             p[x]=y;
            sumw[y]+=sumw[x];
            sumc[y]+=sumc[x];
         }
     }
     //把所有祖先做成背包(每个祖先代表一个搭配集合) 
     int cnt=0;
     for(int i=1;i<=n;i++) if(p[i]==i){
         ++cnt;
         w[cnt]=sumw[i];
         c[cnt]=sumc[i];
     }
     //0-1背包求最大值 
     for(int i=1;i<=cnt;i++)
        for(int j=C;j>=w[i];j--)
           f[j]=max(f[j],f[j-w[i]]+c[i]);
     printf("%d\n",f[C]);
    return 0;
 }
点击查看AC代码

1388:家谱(gen)

//1388:家谱(gen) 
#include<iostream>
using namespace std;
string xm1[27][50001],xm[50001];
int num[27],xmn[27][5001],fa[50001],tot,root;
int find(string s)
{
    int f=0,sz=s[0]-'A'+1;
    for(int i=1;i<=num[sz];i++)
    {
        if(xm1[sz][i]==s)
        {
            f=xmn[sz][i];
            break;
        }
    }
    return f;
}
int zx(int x)
{
    while(fa[x]!=x)
    {
        x=fa[x];
    }
    return fa[x];
}
void add(string s)
{
    int sz=s[0]-'A'+1;
    xm[++tot]=s;
    xm1[sz][++num[sz]]=s;
    xmn[sz][num[sz]]=tot;
    fa[tot]=tot;
}
int main()
{
    string s,txm;
    int sz,f;
    char ch;
    while(cin>>s&&s!="$")
    {
        ch=s[0],txm=s.substr(1,s.length() -1);
        if(ch=='?')
            cout<<txm<<' '<<xm[zx(find(txm))]<<endl;
        else
        {
            sz=find(txm);
            if(sz==0)
            {
                add(txm);
                sz=tot;
            }
            if(ch=='#')root=zx(sz);
            else fa[sz]=root;
        }
    }
//    for(int i=1;i<=tot;i++)
//        cout<<i<<xm[i]<<' ';
//    cout<<endl;
//    for(int i=1;i<=tot;i++)
//        cout<<i<<xm[fa[i]]<<' ';
//    cout<<endl;
//    for(int i=1;i<=26;i++)
//        for(int j=1;j<=num[i];j++)
//            cout<<j<<xm1[i][j]<<' ';
    return 0;
}
点击查看AC代码

1389:亲戚

#include<cstdio>
#include<cstring>
const int N=1e5+1;
int fa[N],n,m,num[N];
int find(int x)
{
    if(x==fa[x])return x;;
    return fa[x]=find(fa[x]);
}
int main()
{
    char ch[2];
    int a,b,zx,zy;
    scanf("%d %d",&n,&m);
    for(int i=1;i<=n;i++)fa[i]=i,num[i]=1;
    
    for(int i=1;i<=m;i++)
    {
        scanf("%s %d",ch,&a);
        zx=find(a);
        if(ch[0]=='M')
        {
            scanf("%d",&b);
            zy=find(b);
            if(zy!=zx)fa[zy]=zx,num[zx]+=num[zy];
        }
        else
            printf("%d\n",num[zx]);
    }
    return 0;
}
点击查看AC代码

1390:食物链【NOI2001】

#include <cstdio>

inline int read() {
    char c = getchar(); int n = 0;
    while (c < '0' || c > '9') { c = getchar(); }
    while (c >= '0' && c <= '9') { n = (n << 1) + (n << 3) + (c & 15); c = getchar(); }
    return n;
}

const int maxN = 100005;

int n, m, ans, fa[maxN * 3];

int find(int u) { return fa[u] == u ? u : fa[u] = find(fa[u]); }

int main() {
    n = read(), m = read();
    for (int i = 1; i <= n * 3; i++) { fa[i] = i; }
    for (; m; m--) {
        int opt = read(), u = read(), v = read();
        if (u > n || v > n) { ans++; continue; }
        if (opt == 1) {
            if (find(u + n) == find(v) || find(u) == find(v + n)) { ans++; }
            else {
                fa[find(u)] = find(v);
                fa[find(u + n)] = find(v + n);
                fa[find(u + n + n)] = find(v + n + n);
            }
        } else {
            if (find(u) == find(v) || find(u) == find(v + n)) { ans++; }
            else {
                fa[find(u + n)] = find(v);
                fa[find(u + n + n)] = find(v + n);
                fa[find(u)] = find(v + n + n);
            }
        }
    }
    printf("%d\n", ans);
    return 0;
}
点击查看AC代码

第五节 最小生成树

1348:【例4-9】城市公交网建设问题

//1348:【例4-9】城市公交网建设问题 
#include<iostream>
using namespace std;
int const N=101;
int const inf=1e9;
int fa[N],n,m,hp,cnt,rd[N][N],dd[N][N];
struct link{
    int x,y,s;
}b[N*N],heap[N*N];
void jh(int &x,int &y)
{
    int t=y;
    y=x;
    x=t;
    return;
}
void put(link x)
{
    heap[++hp]=x;
    int now=hp,next;
    link a,b;
    while(now>1)
    {
        next=now/2;
        a=heap[now],b=heap[next];
        if(a.s>b.s)break;
        heap[now]=b,heap[next]=a;
        now=next;
    }
}
link get()
{
    link x=heap[1];
    heap[1]=heap[hp--];
    int now=1,next;
    link a,b;
    while(now*2<=hp)
    {
        next=now*2;
        a=heap[now];
        if(next<hp&&heap[next+1].s<heap[next].s)next++;
        b=heap[next];
        if(a.s<b.s)break;
        heap[now]=b,heap[next]=a;
        now=next;
     } 
    return x;
}
int find(int x)
{
    if(fa[x]!=x)fa[x]=find(fa[x]);
    return fa[x];
}
int main()
{
    ios::sync_with_stdio(0);
    link t;
    
    cin>>n>>m;
    
    for(int i=1;i<n;i++)
    {
        fa[i]=i;
        for(int j=i+1;j<=n;j++)
            dd[i][j]=inf;
    }
    for(int i=1;i<=m;i++)
    {        
        int x,y,s;
        cin>>x>>y>>s;
        if(x>y)jh(x,y);
        if(dd[x][y]>s)
            dd[x][y]=s;
    }
    cnt=0;
    for(int i=1;i<n;i++)
        for(int j=i+1;j<=n;j++)
            if(dd[i][j]!=inf)
            {
                b[++cnt].x=i;
                b[cnt].y=j;
                b[cnt].s=dd[i][j];
                put(b[cnt]); 
            }
    cnt=1;
    while(cnt<n&&hp)
    {
        t=get();
        int t1=find(t.x),t2=find(t.y);
        if(t1!=t2)
        {
            fa[t2]=t1;
            rd[t.x][t.y]=1;
            cnt++;
        }
    }
    cnt=1;
    for(int i=1;i<n;i++)
        for(int j=i+1;j<=n;j++)
            if(rd[i][j])cout<<i<<"  "<<j<<endl;
    return 0;
}
点击查看AC代码

1349:【例4-10】最优布线问题

//1349:【例4-10】最优布线问题
#include<iostream>
#include<queue>
using namespace std;
int const N=101;
struct link{
    int x,y,s;
    bool operator < (const link t)const
    {return t.s<s;}
}f[N*N];
int fa[N],n,cnt,ans;
priority_queue<link>heap;
int find(int x)
{
    if(fa[x]!=x)fa[x]=find(fa[x]);
    return fa[x];
 } 
int main()
{
    ios::sync_with_stdio(0);
    int tx,ty;
    link t;
    cin>>n;
    for(int i=1;i<=n;i++)fa[i]=i;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
        {
            cin>>tx;
            if(j>i)
            {
                f[++cnt].x=i;
                f[cnt].y=j;
                f[cnt].s=tx;
                heap.push(f[cnt]);
            }
         } 
//    while(heap.size())
//    {
//        link t=heap.top();
//        cout<<t.x<<' '<<t.y<<' '<<t.s<<endl;
//        heap.pop();
//    }
    cnt=1;
    while(cnt<n)
    {
        t=heap.top();
        tx=t.x,ty=t.y;
        tx=find(tx),ty=find(ty);
        if(tx!=ty)
        {
            fa[ty]=tx;
            ans+=t.s;
            cnt++;
        }
        heap.pop();
    }
    cout<<ans;
    return 0;
}
点击查看AC代码

1350:【例4-11】最短网络(agrinet)

//1350:【例4-11】最短网络(agrinet)
#include<iostream>
#include<queue>
using namespace std;
int const N=101;
struct link{
    int x,y,s;
    bool operator < (const link t)const
    {return t.s<s;}
}f[N*N];
int fa[N],n,cnt,ans;
priority_queue<link>heap;
int find(int x)
{
    if(fa[x]!=x)fa[x]=find(fa[x]);
    return fa[x];
 } 
int main()
{
    ios::sync_with_stdio(0);
    int tx,ty;
    link t;
    cin>>n;
    for(int i=1;i<=n;i++)fa[i]=i;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
        {
            cin>>tx;
            if(j>i)
            {
                f[++cnt].x=i;
                f[cnt].y=j;
                f[cnt].s=tx;
                heap.push(f[cnt]);
            }
         } 
//    while(heap.size())
//    {
//        link t=heap.top();
//        cout<<t.x<<' '<<t.y<<' '<<t.s<<endl;
//        heap.pop();
//    }
    cnt=1;
    while(cnt<n)
    {
        t=heap.top();
        tx=t.x,ty=t.y;
        tx=find(tx),ty=find(ty);
        if(tx!=ty)
        {
            fa[ty]=tx;
            ans+=t.s;
            cnt++;
        }
        heap.pop();
    }
    cout<<ans;
    return 0;
}
点击查看AC代码

1351:【例4-12】家谱树

//1351:【例4-12】家谱树
#include<iostream>
using namespace std;
int m[101],n,tx;
bool f[101][101];
int main()
{
    ios::sync_with_stdio(0);
    cin>>n;
    for(int i=1;i<=n;i++)
    {
        cin>>tx;
        m[i]=i;
        while(tx)
        {
            f[i][tx]=true;
            cin>>tx;
        }
    }
    for(int k=1;k<=n;k++)
        for(int i=1;i<=n;i++)
            for(int j=1;j<=n;j++)
            if(i!=j&&j!=k&&i!=k)
                f[i][j]=f[i][j]||f[i][k]&&f[k][j];
    
    for(int i=n;i>=1;i--)
        for(int j=1;j<i;j++)
            if(f[m[i]][m[j]])swap(m[j],m[i]);
    for(int i=1;i<n;i++)cout<<m[i]<<' ';
    cout<<m[n]<<endl;    
    return 0;
}
点击查看AC代码

1391:局域网(net)

//1391:局域网(net)
#include<iostream>
#include<queue>
using namespace std;
int const N=101;
struct link{
    int x,y,s;
    bool operator < (const link t)const
    {return t.s<s;}
}f[N*N];
int fa[N],n,m,cnt,ans,sum;
priority_queue<link>heap;
int find(int x)
{
    if(fa[x]!=x)fa[x]=find(fa[x]);
    return fa[x];
 } 
int main()
{
    ios::sync_with_stdio(0);
    int tx,ty,tz;
    link t;
    cin>>n>>m;
    for(int i=1;i<=n;i++)fa[i]=i;
    for(int i=1;i<=m;i++)
    {
        cin>>tx>>ty>>tz;
        sum+=tz;
        f[i].x=tx;
        f[i].y=ty;
        f[i].s=tz;
        heap.push(f[i]);
     } 
    cnt=1;
    while(cnt<n)
    {
        t=heap.top();
        tx=t.x,ty=t.y;
        tx=find(tx),ty=find(ty);
        if(tx!=ty)
        {
            fa[ty]=tx;
            ans+=t.s;
            cnt++;
        }
        heap.pop();
    }
    cout<<sum-ans<<endl;
    return 0;
}
点击查看AC代码

1392:繁忙的都市(city)

//1392:繁忙的都市(city)
#include<iostream>
#include<queue>
using namespace std;
int const N=301;
struct link{
    int x,y,s;
    bool operator < (const link t)const
    {return t.s<s;}
}f[N*N];
int fa[N],n,m,cnt,ans;
priority_queue<link>heap;
int find(int x)
{
    if(fa[x]!=x)fa[x]=find(fa[x]);
    return fa[x];
 } 
int main()
{
    ios::sync_with_stdio(0);
    int tx,ty,tz;
    link t;
    cin>>n>>m;
    for(int i=1;i<=n;i++)fa[i]=i;
    for(int i=1;i<=m;i++)
    {
        cin>>tx>>ty>>tz;
        f[i].x=tx;
        f[i].y=ty;
        f[i].s=tz;
        heap.push(f[i]);
     } 
    cnt=1;
    while(cnt<n)
    {
        t=heap.top();
        tx=t.x,ty=t.y;
        tx=find(tx),ty=find(ty);
        if(tx!=ty)
        {
            fa[ty]=tx;
            ans=t.s;
            cnt++;
        }
        heap.pop();
    }
    cout<<n-1<<' '<<ans<<endl;
    return 0;
}
点击查看AC代码

1393:联络员(liaison)

//1393:联络员(liaison)
#include<iostream>
#include<queue>
using namespace std;
int const N=2001;
struct link{
    int x,y,s;
    bool operator < (const link t)const
    {return t.s<s;}
}f[N*N];
int fa[N],b[N][N],n,m,cnt,ans;
priority_queue<link>heap;
int find(int x)
{
    if(fa[x]!=x)fa[x]=find(fa[x]);
    return fa[x];
 } 
int main()
{
    ios::sync_with_stdio(0);
    int p,tx,ty,tz;
    link t;
    cin>>n>>m;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            b[i][j]=1e9;
    for(int i=1;i<=n;i++)fa[i]=i;
    for(int i=1;i<=m;i++)
    {
        cin>>p>>tx>>ty>>tz;
        if(p==1)
        {
            ans+=tz;
            tx=find(tx);
            ty=find(ty);
            if(tx!=ty)fa[ty]=tx;
        }
        else
        {
            if(b[tx][ty]>tz)
                b[tx][ty]=tz;
        }
    }
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            if(b[i][j]<1e9)
            {
                f[++cnt].x=i;
                f[cnt].y=j;
                f[cnt].s=b[i][j];
                heap.push(f[cnt]);
            }
    while(!heap.empty())
    {
        t=heap.top();
        tx=t.x,ty=t.y;
        tx=find(tx),ty=find(ty);
        if(tx!=ty)
        {
            fa[ty]=tx;
            ans+=t.s;
            cnt++;
        }
        heap.pop();
    }
    cout<<ans<<endl;
    return 0;
}
点击查看AC代码

1394:连接格点(grid)

//1394:连接格点(grid)
#include<iostream>
using namespace std;
const int N=1e6+1;
int n,m,fa[N],num[N],sum,row[1000],ans;
int find(int x)
{
    if(fa[x]!=x)fa[x]=find(fa[x]);
    return fa[x];
 } 

int main()
{
    ios::sync_with_stdio(0);
    cin>>m>>n;
    int x1,y1,x2,y2,a,b;
    for(int i=1;i<=n*m;i++)num[i]=1,fa[i]=i;
    while(cin>>x1)
    {
        cin>>y1>>x2>>y2;
        a=x1*n+y1-n;
        b=x2*n+y2-n;
        a=find(a),b=find(b);
        if(a!=b)
        {
            fa[b]=a,num[a]+=num[b];
            if(y1!=y2)
                if(y1<y2)row[y1]=1;
                else row[y2]=1;
        }
    }
    for(int i=1;i<n;i++)sum+=row[i];
    ans=(m+1)*n-2-sum;
    for(int i=1;i<=n*m;i++)
    {
        a=find(i);
        if(a==i&&num[a]!=1)ans-=num[a]-1;
    }
    cout<<ans<<endl;
    return 0;
}
点击查看AC代码

第六节 拓扑排序与关键路径

1352:【例4-13】奖金

//1352:【例4-13】奖金
#include<iostream>
#include<queue>
using namespace std;
struct link{
    int pre,to;
}f[20001];
int n,m,last[10001],q[10001],num[10001],cnt,rd=0,money,k;
int main()
{
    ios::sync_with_stdio(0);
    int x,y;
    cin>>n>>m;
    for(int i=1;i<=m;i++)
    {
        cin>>x>>y; 
        num[x]++;
        f[i].pre=last[y];
        f[i].to=x;
        last[y]=i;
    }
    while(cnt<n)
    {
        rd=0;
        for(int i=1;i<=n;i++)
            if(num[i]==0)
            {
                rd++,cnt++,num[i]=1e9;
                q[rd]=i,money+=100;
            }
        if(rd==0)break;
        money+=k*rd;
        k++;
        for(int j=1;j<=rd;j++)
            for(int i=last[q[j]];i;i=f[i].pre)num[f[i].to]--;
    }
    if(cnt==n)cout<<money<<endl;
    else cout<<"Poor Xed\n";
    return 0;
}
点击查看AC代码

1395:烦人的幻灯片(slides)

//1395:烦人的幻灯片(slides)
#include<iostream>
using namespace std;
int n,msg[27][27],num[27],zm[27][5],ans[27],cnt;
int main()
{
    ios::sync_with_stdio(0);
    int x,y;
    cin>>n;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=4;j++)
            cin>>zm[i][j];
    for(int i=1;i<=n;i++)
    {
        cin>>x>>y;
        for(int k=1;k<=n;k++)
            if(zm[k][1]<=x&&x<=zm[k][2]&&zm[k][3]<=y&&y<=zm[k][4])
                msg[k][i]=1,num[k]++;
    }
//    for(int i=1;i<=n;i++)
//    {
//        cout<<num[i]<<':';
//        for(int j=1;j<=n;j++)
//            cout<<msg[i][j]<<' '; 
//        cout<<endl;
//    }
    while(1)
    {
        cnt=0;
        for(int i=1;i<=n;i++)
            if(num[i]==1)
            {
                cnt++;
                num[i]=-1;
                for(int j=1;j<=n;j++)
                    if(msg[i][j])
                    {
                        ans[cnt]=j;
                        break;
                    }
            }
        if(cnt==0)break;
        for(int i=1;i<=cnt;i++)
        { 
            x=ans[i];
            for(int j=1;j<=n;j++)
                if(num[j]>0&&msg[j][x])
                    msg[j][x]=0,num[j]--;            
        }
    }
    for(int i=1;i<=n;i++)
        if(num[i]!=-1)
        {
            cout<<"None\n";
            return 0;
        }
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            if(msg[i][j])
            {
                cout<<char(i-1+'A')<<' '<<j<<endl;
                break;
            }
    return 0;
}
点击查看AC代码

1396:病毒(virus)

//1396:病毒(virus)
#include<iostream>
using namespace std;
int const N=5e4+1;
int n,k;
string s[N],ss,sans;
bool gz[26][26],p[26];//gz[x][y]表示第x个字母的原字母比第y个字母的原字母靠后 
int f[27],cnt,num[27],ans,key[27];
int main()
{
    ios::sync_with_stdio(0);
    for(int i=0;i<27;i++)key[i]=-32;
    int x,y; 
    cin>>k;
    for(int i=1;i<=k;i++)
    {
        cin>>s[i];
        for(int j=0;j<s[i].length() ;j++)
            p[s[i][j]-'a']=true;//收集用到哪些字母 
    }
    cin>>ss;
    for(int i=1;i<k;i++)
    {
        for(int j=0;j<s[i].length() &&j<s[i+1].length();j++)
        {
            x=s[i][j]-'a',y=s[i+1][j]-'a';
            if(x!=y){gz[y][x]=true;break;}//前面字母相同看下一个字母 ,否则不用看后面字母 
            //后排字母应该比前排字母靠后,以此建立排序规则 
        }
    }
    for(int i=0;i<26;i++)//把所用到字母建立一个1-n的映射 
        if(p[i])f[++cnt]=i;
    n=cnt;
    //根据规则建立有向图,并统计有向图入度 
    for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
            if(i!=j&&gz[f[i]][f[j]])num[f[i]]++;
    cnt=0;
    while(cnt<n)
    {
        k=0;
        for(int i=1;i<=n;i++)
        {
            if(num[f[i]]==0)//入度为0说明对应字母应排前面,第x个入度为0的字母应是用到的第x个字母 
            {
                k++;
                ans=f[i];
                num[f[i]]=-1; 
            }
        }
        if(k!=1)//字典无错必只有一个入度为0点 
        {
            cout<<0<<endl;
            return 0;
        }
        for(int i=1;i<=n;i++)//去掉己确认点的所有关联及入度统计量 
            if(gz[f[i]][ans])gz[f[i]][ans]=false,num[f[i]]--;
        key[ans]=f[++cnt];//确认对应关系 
    }
    for(int i=0;i<ss.length() ;i++)
    {
        k=key[ss[i]-'a'];
        if(k<0)//字典不全 
        {
            cout<<0<<endl;
            return 0;
        }
        sans+=char(k+'a');
    }
    cout<<sans;
    return 0;
}
点击查看AC代码

点击查看AC代码

posted @ 2019-02-16 17:06  耍人  阅读(10283)  评论(0编辑  收藏  举报