乘积最大_蓝桥杯第九届 _Java

import java.util.Arrays;
import java.util.Scanner;

public class Max_product2 {
	public static void main(String[] args) {
		Scanner in = new Scanner(System.in);
		int n = in.nextInt();
		int k = in.nextInt();
		int mod = 1000000009;
		int[] a = new int[n];
		for (int i = 0; i < n; i++) {
			a[i] = in.nextInt();
		}
		in.close();
		Arrays.sort(a);
		//初始化双指针
		int l = 0;
		int r = n-1;
		long res = 1;
		int flag = 1;
		if(k % 2 == 1) {//如果k是奇数,先挑出一个最大的
			res = (long)a[n-1];//奠定答案是正是负的基调。因为下面的x和y一定都是正数
			if(a[n-1] < 0) flag = -1;//证明全是负数	
			r--;//右指针移动
			k--;
		}
		while (k != 0) {
			long x = (long)a[l] * a[l + 1] , y = (long)a[r] * a[r - 1];//两边同时取对
			if(x*flag > y*flag) { //如果flag为-1,这里巧妙的比较负数的大小。而不是绝对值的大小
				//不可以写成是 res % mod * x % mod,因为res是一定小于mod的。而(res*x)不一定没超出范围,x才是未知的,应该先把x%mod,让x缩小,再乘以res。最后再%mod
				res = x % mod * res % mod;
				l += 2;//左指针移动
			}else {
				res = y % mod * res % mod;
				r -= 2;//右指针移动			
			}	
			k -= 2;
		}

		System.out.println(res);


	}
}

思路:既然要最大值,我们先排序。观察看看。列举所有可能的情况并且不能有遗漏,最好简洁。我们从k的奇偶入手。
1.k是偶数。1)负数是偶数。那么答案肯定是正数。因为如果必须要选,我们只选偶数个负数就好了。负负得正。
                  2)负数是奇数。那么答案肯定也是正数。因为如果必须要选,我们只选奇数中偶数个负数就好了。负负得正。
2.k是奇数。1)负数是偶数。那么。。。(跟上面一模一样)
                  4)特殊性,如果k是奇数,并且所有数字都是负数,那么答案一定是负数。(答案为负只有这一种情况)
为了让代码利用性高。当k是奇数时,我们可以先挑选一个最大的数字当作初始res,此时k就变成偶数了。我们跳到上面的代码,把最大值算出来,再和这个res相乘,就是最大乘积了。

写的乱乱的。因为我是做错了,到网上看答案自己再做一遍的。其中错了好几次,因为我是看了大概思路自己做的,不是直接抄哒。代码都懂了现在但是以后出这样的题不一定自己能想出来。如果有疑问的地方可以问我噢,我肯定能解答。
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值