接着盘Java,接着写题,还有一场cf

目录

包装类

单例设计模式

类的成员——初始化块

final关键字

抽象类

模块设计模式

接口

类的成员——内部类

集合

HashSet集合 

TreeSet集合 

List集合

map集合

工具类conllections

泛型

泛型类 

 泛型接口

报错的情况 

 泛型方法

 泛型通配符

有限制的通配符

cf


包装类

Java有一个非常明显的特点,它有很多类,类中有方法,用户可以通过调用类,来解决问题,与其自己再创造类,学会调用已知的类,效果可能会更好。

 

 

 

 

单例设计模式

 一般new对象太费力,或者需要频繁地new新的但没有必要的对象,就使用单例设计模式。

 

 

 

类的成员——初始化块

 

final关键字

对变量起限制作用

 

 

final修饰的方法不能被子类重写。

 

 

抽象类

abstract关键字

只要类中有一个抽象方法,类就必须是抽象类、

 

 

模块设计模式

抽象类体现的就是一种模块模式的设计,它作为多个子类的通用模板。

 

 

接口

父类一般不要去改,因为一旦改了父类,它下面的子类就会受影响,但是有时候又确实需要对父类扩展方法,一般这种时候就新建接口,然后再在接口上新建方法,其它的子类有类似需求的,也可以新建接口。

通俗点讲就是,父类已经满足不了子类的需求了,那我就要自食其力去创建这个东西,自食其力创建的就是接口。

 

 

 

 

类的成员——内部类

 

集合

HashSet集合 

 

 

 

 

TreeSet集合 

 

 

List集合

 

map集合

 

 ​​​​​

 

 

 

工具类conllections

 ​​​​​​​

 

泛型

让集合添加我指定的类型,从而限制类型,更安全。

泛型类 

 泛型接口

 

报错的情况 

 

 泛型方法

 

 

 泛型通配符

 

有限制的通配符

 

 

 

简单搜索&&进阶搜索 - Virtual Judge 

分析:

这个题目究其本质就是一个全排列,但是要记得回溯。

具体实现就是创建一个二维数组,对可以连接i的每个元素的值都赋1,然后这其实就已经实现了字典序的排列,然后从起点开始找,回到起点就结束,然后输出。

#include<stdio.h>
#include<math.h>
#include<string.h>
int m;
int a[21][21],aa[25];
int b[25];
int k=1;
void dfs(int c,int d)
{
	if(d==20&&!a[c][m])
	return;
	if(d==20&&a[c][m])
	{
		printf("%d:  ",k);
		k++;
		for(int i=0;i<20;i++)
		printf("%d ",aa[i]);
		printf("%d",m);
		printf("\n");
		return;
	}
	for(int i=1;i<=20;i++)
	{
		if(a[i][c]&&!b[i])
		{
			b[i]=1;
			aa[d]=i;
			dfs(i,d+1);
			b[i]=0;
		}
	}
}

int main()
{
	for(int i=1;i<=20;i++)
	{
		int x,y,z;
		scanf("%d%d%d",&x,&y,&z);
		a[i][x]=1;
		a[i][y]=1;
		a[i][z]=1;
	}
	scanf("%d",&m);
	while(m)
	{
		k=1;
		aa[0]=m;
		for(int i=0;i<21;i++)
		b[i]=0;
		b[m]=1;
		dfs(m,1);
		scanf("%d",&m);
	}
}

https://vjudge.net/contest/547627#problem/G

分析:

这个题可以用双向广搜,但是我是用了两次广搜,然后加起来比较找最小。

这里有一个小坑点就是,判断哪个kfc的距离最短的时候,还要判断这两个人是否都能到这个kfc,但凡有一个人没有到,这个kfc都不能作为两个人会面的场所。

还有就是她们两个走过的地方都必须标记并且记录以便于判断。

#include<stdio.h>
#include<math.h>
#include<string.h>
int m,n;
int a[2][201][201],xx,yy,k;
char c[201][201],cc;
int b[201][201];
int d[4][2]={{0,1},{0,-1},{1,0},{-1,0}};

struct fff
{
	int x;
	int y;
	int s;
}map[201*201];

void cz(char ccc)
{
	for(int i=0;i<n;i++)
	{
		for(int j=0;j<m;j++)
		if(c[i][j]==ccc)
		{
			xx=i;
			yy=j;
			return;
		}
	}
}

void bfs()
{
	int tail,head;
	tail=head=1;
	cz(cc);
	map[tail].x=xx;
	map[tail].y=yy;
	map[tail].s=0;
	b[xx][yy]=1;
	tail++;
	while(head<tail)
	{
		for(int i=0;i<4;i++)
		{
			int nx=map[head].x+d[i][0];
			int ny=map[head].y+d[i][1];
			if(nx<0||nx>=n||ny<0||ny>=m||b[nx][ny]||c[nx][ny]=='#')
			continue;
			b[nx][ny]=1;
			map[tail].x=nx;
			map[tail].y=ny;
			map[tail].s=map[head].s+1;
			a[k][nx][ny]=map[tail].s;
			tail++;
		}
		head++;
	}
}

void minn()
{
	int min=400000;
	for(int i=0;i<n;i++)
	{
		for(int j=0;j<m;j++)
		{
			if(c[i][j]=='@'&&a[0][i][j]&&a[1][i][j])
			{
				if(a[0][i][j]+a[1][i][j]<min)
				min=a[0][i][j]+a[1][i][j];
			}
		}
	}
	printf("%d\n",min*11);
}

int main()
{
	while(scanf("%d%d",&n,&m)!=EOF)
	{
		for(int i=0;i<n;i++)
		scanf("%s",c[i]);
		//for(int i=0;i<n;i++)
		//printf("%s\n",c[i]);
		k=0;
		cc='Y';
		for(int i=0;i<201;i++)
		for(int j=0;j<201;j++)
		b[i][j]=0;
		bfs();
		k=1;
		cc='M';
		for(int i=0;i<201;i++)
		for(int j=0;j<201;j++)
		b[i][j]=0;
		bfs();
		minn();
		for(int z=0;z<2;z++)
		for(int i=0;i<201;i++)
		for(int j=0;j<201;j++)
		a[z][i][j]=0;
	}
}

简单搜索&&进阶搜索 - Virtual Judge

分析:

这个题主打的就是一个记录,记录路径,记录次数。(副主打判断)

我写得有点臃肿,但思路没什么大问题,它还是一个广搜,但是它的结构要多的就是它的记录它之前做的动作,进入循环先判断,是不是达到了要求的水量,达到就输出,根据记录的路径选择性的输出,在搜索时它一共有6个状态,所以对于每一个“head”都要判断六次。

它每一次倒水都要进行记录,记住是每一次,记住这个路径,之后直接输出就行。

这个题没有坑点,但是脑袋一定要清楚,我下面该判断什么,该怎么判断,判断成功怎么赋值,怎么给路径。

#include<stdio.h>
#include<math.h>
#include<string.h>
int a,b,c;
int book[1005][1005];
struct fff
{
    int aa;
    int bb;
    int bs;
    int k;
    char jl[1005];
}arr[1005*1005];

void bfs()
{
    int tail,head;
    head=tail=0;
    arr[tail].aa=0;
    arr[tail].bb=0;
    arr[tail].bs=0;
    book[0][0]=1;
    arr[tail].k=0;
    arr[tail].jl[0]=0;
    tail++;
    while(head<tail)
    {
        struct fff p=arr[head++];
        if(p.aa==c||p.bb==c)
        {
            printf("%d\n",p.bs);
            for(int i=0;i<p.k;i++)
            {
                switch (p.jl[i])
                {
                    case '0':
                    printf("FILL(1)\n");
                    break;
                    case '1':
                    printf("FILL(2)\n");
                    break;
                    case '2':
                    printf("DROP(1)\n");
                    break;
                    case '3':
                    printf("DROP(2)\n");
                    break;
                    case '4':
                    printf("POUR(1,2)\n");
                    break;
                    case '5':
                    printf("POUR(2,1)\n");
                    break;
                }
            }
            return;
        }
        for(int i=0;i<6;i++)
        {
            if(i==0&&!book[a][p.bb])//倒满a
            {
                book[a][p.bb]=1;
                arr[tail].aa=a;
                arr[tail].bb=p.bb;
                arr[tail].bs=p.bs+1;
                strcpy(arr[tail].jl,p.jl);
                arr[tail].jl[p.k]=i+'0';
                arr[tail].k=p.k+1;
                arr[tail].jl[arr[tail].k]=0;
                tail++;
            }
            if(i==1&&!book[p.aa][b])//倒满b
            {
                book[p.aa][b]=1;
                arr[tail].aa=p.aa;
                arr[tail].bb=b;
                arr[tail].bs=p.bs+1;
                strcpy(arr[tail].jl,p.jl);
                arr[tail].jl[p.k]=i+'0';
                arr[tail].k=p.k+1;
                arr[tail].jl[arr[tail].k]=0;
                tail++;
            }
            if(i==2&&!book[0][p.bb])//倒掉a
            {
                book[0][p.bb]=1;
                arr[tail].aa=0;
                arr[tail].bb=p.bb;
                arr[tail].bs=p.bs+1;
                strcpy(arr[tail].jl,p.jl);
                arr[tail].jl[p.k]=i+'0';
                arr[tail].k=p.k+1;
                arr[tail].jl[arr[tail].k]=0;
                tail++;
            }
            if(i==3&&!book[p.aa][0])//倒掉B
            {
                book[p.aa][0]=1;
                arr[tail].aa=p.aa;
                arr[tail].bb=0;
                arr[tail].bs=p.bs+1;
                strcpy(arr[tail].jl,p.jl);
                arr[tail].jl[p.k]=i+'0';
                arr[tail].k=p.k+1;
                arr[tail].jl[arr[tail].k]=0;
                tail++;
            }
            if(i==4)//把a倒给b
            {
                struct fff q;
                q.bb=p.aa+p.bb;
                if(q.bb<b&&!book[0][q.bb])
                {
                    book[0][q.bb]=1;
                    arr[tail].aa=0;
                    arr[tail].bb=q.bb;
                    arr[tail].bs=p.bs+1;
                    strcpy(arr[tail].jl,p.jl);
                arr[tail].jl[p.k]=i+'0';
                arr[tail].k=p.k+1;
                arr[tail].jl[arr[tail].k]=0;
                    tail++;
                }
                else if(q.bb>=b&&!book[q.bb-b][b])
                {
                    book[q.bb-b][b]=1;
                    arr[tail].aa=q.bb-b;
                    arr[tail].bb=b;
                    arr[tail].bs=p.bs+1;
                    strcpy(arr[tail].jl,p.jl);
                arr[tail].jl[p.k]=i+'0';
                arr[tail].k=p.k+1;
                arr[tail].jl[arr[tail].k]=0;
                    tail++;
                }
            }
             if(i==5)//把b倒给a
            {
                struct fff q;
                q.aa=p.aa+p.bb;
                if(q.aa<a&&!book[q.aa][0])
                {
                    book[q.aa][0]=1;
                    arr[tail].aa=q.aa;
                    arr[tail].bb=0;
                    arr[tail].bs=p.bs+1;
                    strcpy(arr[tail].jl,p.jl);
                arr[tail].jl[p.k]=i+'0';
                arr[tail].k=p.k+1;
                arr[tail].jl[arr[tail].k]=0;
                    tail++;
                }
                else if(q.aa>=a&&!book[a][q.aa-a])
                {
                    book[a][q.aa-a]=1;
                    arr[tail].aa=a;
                    arr[tail].bb=q.aa-a;
                    arr[tail].bs=p.bs+1;
                    strcpy(arr[tail].jl,p.jl);
                arr[tail].jl[p.k]=i+'0';
                arr[tail].k=p.k+1;
                arr[tail].jl[arr[tail].k]=0;
                    tail++;
                }
            }
        }
    }
     printf("impossible\n");
}

int main()
{
    scanf("%d%d%d",&a,&b,&c);
    bfs();
}

cf

这场cf的第一题没什么难度,其实第二题也没什么难度,但是自己想岔了一个点,就一直出不来。

Problem - B - Codeforces

分析:

首先要明白它这个数组里面的数是可以随意变换位置的,也就是说你想让它放在哪里就放在哪里,所以我最开始的想法的就是以0的个数为界限,分为三大块。第一大块,全是0的情况,那结果就是1;第二大块,0比非0数的个数少的情况,那么那些非零数是可以插空的,所以结果为0;第三大块,也就是我昨天出问题的地方,我多想了一个3,我当时想着如果0比非零数的个数多,我就把所有的非零数往后堆,那就会出现“00000111”的情况,我觉得就是3,但是其实不是,如果把它插空“01010100”,那么它的结果应该是2,所以最后一大块的判断分两部分,第一部分,如果它的最大值就是1,那么结果是2;如果最大值比1大,那结果就是1,就像“00000311”,这里的原理就是只要我的最大比1大,那我就把这个最大值放在一堆数的最前面,后面的数两两相加,一定都会大于或等于2.

代码如下:

#include<stdio.h>
#include<math.h>
#include<string.h>
int main()
{
    int t;
    scanf("%d",&t);
    while(t--)
    {
        int n;
        scanf("%d",&n);
        int l1=0;//0的数量
        int max=-1;
        for(int i=0;i<n;i++)
        {
            int a;
            scanf("%d",&a);
            if(a==0)
            l1++;
            if(max<a)
            max=a;
        }
        if(l1==n)
        printf("1\n");
        else if(l1<=(n+1)/2)
        printf("0\n");
        else if(max==1)
        printf("2\n");
        else 
        printf("1\n");
    }
}

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值