C. Another Array Problem

思路:这个题没想到吧数先往0上搞,然后一直想不出来,为什么要先往0上搞呢,对于每个数来说,它最大只会变成这一堆数的最大值,所以我们考虑能不能变成最大值,那么只要是两个相等的数通过一次操作就可以变为0,那么我们能够发现当n>=4时,一定可以将除了最大值之外的所有数都变为0(假如最大值为i,当i的左边跟右边都至少有两个数时,那么就可以对左边右边分别操作两次,这样操作完之后就会都变成0,即1 2 5 3 4一次变为1 1 5 1 1两次变为0 0 5 0 0,然后变为5 5 5 5 5,而当某一侧只有一个数时,那么另一侧至少有两个数,那么我们可以先将一侧变为0,然后再将它变为最大值,那么就会有至少三个最大值,那么我们再将只有一个的那一侧跟相邻的最大值进行操作先变为0,然后再变为最大值,例如1 2 4 3,操作一次1 1 4 3,操作两次0 0 4 3,操作三次4 4 4 3 操作4次,4 4 1 1操作5次,4 4 0 0,操作6次4 4 4 4),所以我们发现当n>=4时一定可以通过一系列操作将所有的数都变成最大值,那么对于n==1的情况只能是本身,n==2的情况要么不变,要么变,n==3的情况,比较多,当最大值出现在两头是,那么就可以通过操作将所有的数变为最大值,否则如果再中间时,要么左边两个合并一下,要么右边两个合并一下,要么整个合并一下,要么直接全部变为第一个,要么全部变为第3个,要么先左边合并一下然后全部变为第1个,要么先右边合并一下然后全部变为第3个 ,要么不变,n==3的情况比较多,可以仔细想一想

// Problem: C. Another Array Problem
// Contest: Codeforces - Codeforces Round 840 (Div. 2) and Enigma 2022 - Cybros LNMIIT
// URL: https://codeforces.com/problemset/problem/1763/C
// Memory Limit: 256 MB
// Time Limit: 2000 ms

#include<iostream>
#include<cstring>
#include<string>
#include<sstream>
#include<bitset>
#include<deque>
#include<cmath>
#include<cstdio>
#include<algorithm>
#include<cassert>
#include<queue>
#include<map>
#include<stack>
#include<vector> 
#include<set>
#include<cstdlib>
#define fi first
#define se second
#define i128 __int128
using namespace std;
typedef long long ll;
typedef double db;
typedef pair<int,int> PII;
typedef pair<int,pair<int,int> > PIII;
const double eps=1e-7;
const int N=5e5+7 ,M=5e5+7, INF=0x3f3f3f3f,mod=1e9+7,mod1=998244353;
const long long int llINF=0x3f3f3f3f3f3f3f3f;
inline ll read() {ll x=0,f=1;char c=getchar();while(c<'0'||c>'9') {if(c=='-') f=-1;c=getchar();}
while(c>='0'&&c<='9') {x=(ll)x*10+c-'0';c=getchar();} return x*f;}
inline void write(ll x) {if(x < 0) {putchar('-'); x = -x;}if(x >= 10) write(x / 10);putchar(x % 10 + '0');}
inline void write(ll x,char ch) {write(x);putchar(ch);}
void stin() {freopen("in_put.txt","r",stdin);freopen("my_out_put.txt","w",stdout);}
bool cmp0(int a,int b) {return a>b;}
template<typename T> T gcd(T a,T b) {return b==0?a:gcd(b,a%b);}
template<typename T> T lcm(T a,T b) {return a*b/gcd(a,b);}
void hack() {printf("\n----------------------------------\n");}

int T,hackT;
int n,m,k;
int w[N];

void solve() {
	n=read();
	
	for(int i=1;i<=n;i++) w[i]=read();
	
	int maxn=-1;
	for(int i=1;i<=n;i++) maxn=max(maxn,w[i]);
	
	if(n>=4) printf("%lld\n",(ll)maxn*n);
	else {
		if(n==1) printf("%d\n",w[1]);
		else if(n==2) printf("%d\n",max(w[1]+w[2],2*abs(w[2]-w[1])));
		else {
			if(w[1]==maxn||w[3]==maxn) printf("%lld\n",(ll)3*maxn);
			else {
				ll a1=(ll)w[1]+w[2]+w[3];
				ll a2=w[1]+(ll)2*abs(w[2]-w[3]);
				ll a3=w[3]+(ll)2*abs(w[1]-w[2]);
				ll a4=(ll)3*abs(w[1]-w[3]);
				ll a5=(ll)3*abs(w[1]-w[2]);
				ll a6=(ll)3*abs(w[2]-w[3]);
				ll a7=(ll)3*w[1];
				ll a8=(ll)3*w[3];
				
				ll res1=max(a1,a2);
				ll res2=max(a3,a4);
				ll res3=max(a5,a6);
				ll res4=max(a7,a8);
				ll res=max(max(res1,res2),max(res3,res4));
				
				printf("%lld\n",res);
			}
		}
	}
}   

int main() {
    // init();
    // stin();
	//ios::sync_with_stdio(false); 

    scanf("%d",&T);
    // T=1; 
    while(T--) hackT++,solve();
    
    return 0;       
}          

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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值