Birthday Gift

题目:

传送门

来源:牛客网

时间限制:C/C++ 1秒,其他语言2秒
空间限制:C/C++ 262144K,其他语言524288K
64bit IO Format: %lld

题目描述

On Derrick's birthday, Derrick received a gift from his girlfriend Sandy. The gift consists n tiny balls, and each of them has two characteristics a and b. As Derrick is boring, he just wants to play with these balls.
Each time Derrick chooses two balls randomly. For each pair of balls x, y, Derrick defines their beautiful value as min(xa+yb,xb+ya)min(x_a+y_b, x_b+y_a)min(xa​+yb​,xb​+ya​).
Given the properties a and b of all the n tiny balls, Derrick will select exactly two of them and maximum their beautiful value. Now he needs your help, please help him.

输入描述:

Each input file only contains one test case.
The first line contains an integer n (2 ≤ n ≤ 2×10^5), indicating the total number of the tiny balls.
The second line contains n integers a_1,a_2,...,a_n (1 ≤ a_i ≤ 10^9), indicating the characteristic a of each ball.
The third line contains n integers b_1,b_2,...,b_n​ (1 ≤ b_i​ ≤ 10^9), indicating the characteristic b of each ball.

输出描述:

For each test case, output a single integer in a line indicating the maximum beautiful value of the given tiny balls.

示例1

输入

5
1 3 5 4 2
2 4 3 5 3

输出

8

题目给出  n≤2×10^5  以及1s(2s)的时间限制,所以要求代码时间复杂度在O(nlogn)以内

因为要取min(x.a+y.b,x.b+y.a)作为判断条件,我想了较长时间没有想到可以直接在O(nlogn)内处理的可靠的数据结构,像我之前看到的一篇关于简化数据的思路则有在极端数据条件下的时间复杂度不可靠性,在此不做讨论

然后考虑如何简化数据

首先看取值判断条件

令rank=min(x.a+y.b,x.b+y.a)

对于任意一组x,y,当x.a+y.b>x.b+y.a,我们互换x,y的位置不就得到y.a+x.b<=y.b+x.a了吗

那么如果对于任意一组x,y都有x.a+y.b<=x.b+y.a,条件是否就可以简化为rank=x.a+y.b,

bool cmp(node x,node y)
{   return x.a-x.b<y.a-y.b;}

sort(v+1,v+n+1,cmp);

如何保证对于每组x,y都有x.a+y.b<=x.b+y.a呢
设pi=ai-bi;
得到ai+bj=aj+bi+(pi-pj);

可知只要根据pi进行从小到大的排序,便可保证对于任意一组x,y都有x.a+y.b<=x.b+y.a
之后任选方法处理即可
比如设数组max_a,max_b,max_a从i=1处开始计算从1到i区间内ai的最大值,max_b从i=n处计算i到n区间内bi的最大值,然后逐i计算ans=max(ans,max_a+max_b)即为答案

//#include<bits/stdc++.h>
#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
using namespace std;
template< typename Tcin>
void read(Tcin &n)
{
	n=0;Tcin x=1;char c=getchar();
	while(c<'0'||c>'9')
	{	if(c=='-')x=-1;c=getchar();}
	while(c>='0'&&c<='9')
		n=(n<<3)+(n<<1)+(c-'0'),c=getchar();
	n*=x;
}
struct node
{
	int a,b;
}v[100010];
bool cmp(node x,node y)
{   return x.a-x.b<y.a-y.b;}
int max_a[100010],max_b[100010];
int main()
{
	int n;
	read(n);
	for(int i=1;i<=n;i++)
		read(v[i].a);
	for(int i=1;i<=n;i++)
		read(v[i].b);
	sort(v+1,v+n+1,cmp);
	max_a[0]=max_b[n+1]=0;
	for(int i=1;i<=n;i++)
		max_a[i]=max(max_a[i-1],v[i].a);
	for(int i=n;i>0;i--)
		max_b[i]=max(max_b[i+1],v[i].b);
	int ans=0;
	for(int i=1;i<n;i++)
		ans=max(ans,max_a[i]+max_b[i+1]);
	cout<<ans;
	return 0;
}

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值