Codeforces Round #387 (Div. 2)A~D A Display Size D Winter Is Coming

本文介绍了一种算法,用于确定具有特定像素数量的矩形显示屏幕的最佳尺寸,确保行数不超过列数且行列数之差尽可能小。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

A. Display Size
time limit per test
1 second
memory limit per test
256 megabytes
input
standard input
output
standard output

A big company decided to launch a new series of rectangular displays, and decided that the display must have exactly n pixels.

Your task is to determine the size of the rectangular display — the number of lines (rows) of pixels a and the number of columns of pixels b, so that:

  • there are exactly n pixels on the display;
  • the number of rows does not exceed the number of columns, it means a ≤ b;
  • the difference b - a is as small as possible.
Input

The first line contains the positive integer n (1 ≤ n ≤ 106) — the number of pixels display should have.

Output

Print two integers — the number of rows and columns on the display.

Examples
input
8
output
2 4
input
64
output
8 8
input
5
output
1 5
input
999999
output
999 1001
Note

In the first example the minimum possible difference equals 2, so on the display should be 2 rows of 4 pixels.

In the second example the minimum possible difference equals 0, so on the display should be 8 rows of 8 pixels.

In the third example the minimum possible difference equals 4, so on the display should be 1 row of 5 pixels.


wa了一发绝世水题,错在记混了ceil和floor!!做题要长脑子

题目和错的代码都贴上!

#include<stdio.h>
#include<algorithm>
#include<queue>
#include<math.h>
#include<string.h>
using namespace std;
int main()
{
	int n,a,b,i;
	scanf("%d",&n);
	for(i=floor(sqrt(n));i>=1;i--)//错的代码for(i=ceil(sqrt(n));i>=1;i--)
	{
		if(n%i==0)
		{
			a=i;
			b=n/i;
			break;
		}
	}
	printf("%d %d\n",a,b);
}

b水题,不多说

#include<stdio.h>
#include<algorithm>
#include<queue>
#include<string.h>
using namespace std;
int main()
{
	char ch[1000];
	int n,i,x,a,c,g,t;
	scanf("%d",&n);
	getchar();
	a=c=g=t=0;
	scanf("%s",ch);
	if(n%4!=0)
	{
		printf("===\n");
		return 0;
	}
	else
	{
		x=n/4;
		for(i=0;i<n;i++)
		{
			if(ch[i]=='A')
			a++;
			else if(ch[i]=='C')
			c++;
			else if(ch[i]=='G')
			g++;
			else if(ch[i]=='T')
			t++;
		}
		if(a>x||c>x||g>x||t>x)
		{
			printf("===\n");
			return 0;
		}
		a=x-a;
		c=x-c;
		g=x-g;
		t=x-t;
		for(i=0;i<n;i++)
		{
			if(ch[i]=='?')
			{
				if(a)
				{
					ch[i]='A';
					a--;
				}
				else if(c)
				{
					ch[i]='C';
					c--;
				}
				else if(g)
				{
					ch[i]='G';
					g--;
				}
				else if(t)
				{
					ch[i]='T';
					t--;
				}
			}
		}
		printf("%s\n",ch);
	}
	return 0;
}

c记录暴力一下就能过

#include<stdio.h>
#include<algorithm>
#include<queue>
#include<string.h>
using namespace std;
int t[1000006],k[1000006],d[1000006];
int main()
{
	long long int s[200];
	int q,n,i,j,x,xx,ans;
	scanf("%d %d",&n,&q);
	for(i=0;i<n;i++)
	s[i]=1;
	for(i=0;i<q;i++)
	scanf("%d %d %d",&t[i],&k[i],&d[i]);
	for(i=0;i<q;i++)
	{
		x=0;
		for(j=0;j<n;j++)
		{
			if(t[i]>=s[j])
			x++;
		}
		xx=0;
		ans=0;
		if(x>=k[i])
		{
			for(j=0;j<n;j++)
			{
				if(t[i]>=s[j])
				{
					s[j]=t[i]+d[i];
					ans+=(j+1);
					xx++;
					if(xx==k[i])
					break;
				}
			}
			printf("%d\n",ans);
		}
		else
		printf("-1\n");
	}
}

d题最气了,因为刚学完背包,看了题意感觉是个背包,写完结果wa了,一直调,一直想样例,到结束也没过=。=

结束了看了样例才知道,原来是忘记考虑全为负数的情况。。。。。。。。

背包的思想:先遍历找负数的个数 x ,以及每个负数的间隔,可以把给的天数 k 减去负数的个数 x 当做背包的容量,然后把这些间隔想为物品,间隔的天数也就是物品的重量,价值根据间隔在的位置决定,因为如果能把两个负数中间的间隔天数覆盖了,可以节省两次换轮胎次数,把最后的那个间隔去掉,可以节省一次换轮胎次数,所以中间间隔的价值为2,最后的那个间隔价值为1

特判一下全为正或全为负的情况

#include<stdio.h>
#include<algorithm>
#include<queue>
#include<string.h>
struct node
{
	int jian,c;
}yaobai[200005];
using namespace std;
int cmp(node u,node v)
{
	return u.jian<v.jian;
}
int n,k,t[200005],dp[200005];
int main()
{
	int i,x=0,j,begin,la,le,ri,ans,m,flog=1;
	scanf("%d %d",&n,&k);
	for(i=0;i<n;i++)
	scanf("%d",&t[i]);
	memset(dp,0,sizeof(dp));
	for(i=0,j=0;i<n;i++)
	{
		if(t[i]<0)
		{
			x++;
			if(flog)
			{
				la=i;
				flog=0;
			}
			else
			{
				yaobai[j].c=2;
				yaobai[j++].jian=i-la-1;
				la=i;
			}
		}
	}
	if(t[n-1]>=0)
	{
		if(n-la-1>0)
		{
			yaobai[j].c=1;
			yaobai[j++].jian=n-la-1;
		}
	}//找间隔
	if(x==0)
	printf("0\n");
	else if(x>k)
	printf("-1\n");
	else
	{
		
		if(x==n)
		{
			printf("1\n");
		}
		else
		{
			le=i,ri=j;
			sort(yaobai,yaobai+j,cmp);
			i=0;
			m=k-x;
			while(yaobai[i].jian==0)
			{
				x--;
				i++;
			}//把间隔为0的去掉
			ans=2*x;		
			for(i=le;i<ri;i++)
			{
				for(j=m;j>=yaobai[i].jian;j--)
				dp[j]=max(dp[j],dp[j-yaobai[i].jian]+yaobai[i].c);
			}//背包
			if(t[n-1]<0)	
			ans--;	
			ans-=dp[m];
			printf("%d\n",ans);
		}
		
	}
	return 0;
}

其实背包无论实现还是时间都比较长,直接贪心也能过,因为价值只有两种1 和 2,并且价值为1的还最多只有一个,

可以对中间的那些间隔按天数排序,同等价值,先选轻的(天数小的),装不下前面的间隔了,在试试能不能装下最后那个间隔就好了

#include<stdio.h>
#include<algorithm>
#include<queue>
#include<string.h>
struct node
{
	int jian,c;
}yaobai[200005];
using namespace std;
int cmp(node u,node v)
{
	return u.jian<v.jian;
}
int n,k,t[200005],dp[200005];
int main()
{
	int i,x=0,j,begin,la,le,ri,ans,m,flog=1;
	scanf("%d %d",&n,&k);
	for(i=0;i<n;i++)
	scanf("%d",&t[i]);
	memset(dp,0,sizeof(dp));
	for(i=0,j=0;i<n;i++)
	{
		if(t[i]<0)
		{
			x++;
			if(flog)
			{
				la=i;
				flog=0;
			}
			else
			{
				yaobai[j].c=2;
				yaobai[j++].jian=i-la-1;
				la=i;
			}
		}
	}
	if(t[n-1]>=0)
	{
		if(n-la-1>0)
		{
			yaobai[j].c=1;
			yaobai[j++].jian=n-la-1;
		}
	}
	if(x==0)
	printf("0\n");
	else if(x>k)
	printf("-1\n");
	else
	{
		
		if(x==n)
		{
			printf("1\n");
		}
		else
		{
			le=i,ri=j;
			sort(yaobai,yaobai+j,cmp);
			i=0;
			m=k-x;
			while(yaobai[i].jian==0)
			{
				x--;
				i++;
			}
			ans=2*x;		
			for(i=le;i<ri;i++)
			{
				for(j=m;j>=yaobai[i].jian;j--)
				dp[j]=max(dp[j],dp[j-yaobai[i].jian]+yaobai[i].c);
			}
			if(t[n-1]<0)	
			ans--;	
			ans-=dp[m];
			printf("%d\n",ans);
		}
		
	}
	return 0;
}

做的最烂的一次,并且这次前四题暴力都能过。。。。。。


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值