Indeed修改数组行或者列,得到最大数组和

来源:互联网 发布:淘宝等级图 编辑:程序博客网 时间:2024/05/21 18:48

输入

H,W,X,K

int[H][W]

H代表行,W代表列,X代表要替换成的数字,k代表要替换多少行或者列(替换的行列数之和可以小于K).

输出:

各种替换可能中,数组的最大和。


例子:

输入:

8
8
29
14
-89 -76 92 61 5 -18 -68 90
-3 44 -9 84 -36 51 -43 85
11 -72 5 -90 -43 -94 5 97
-90 22 66 29 -26 66 -29 -38
82 -60 60 -9 -23 -8 -59 -13
-4 -68 -4 59 78 25 99 -86
-4 23 21 53 53 -25 -31 -66
38 50 -35 -98 -49 -33 -31 88


output:2100


输入:

3
4
3
2
1 -1 1 1
5 -5 5 5
9 -9 9 9
输出:
60

一开始的想法是直接贪心。每次替换最大增量的行或者列:

代码如下:

import java.io.BufferedReader;import java.io.IOException;import java.io.InputStreamReader;import java.util.HashSet;import java.util.Scanner;import java.util.Set;public class Main {private int H;private int W;private int X;private int K;private int[][] arr;private int sumR[];private int sumC[];public Main() {Scanner sc = new Scanner(System.in);H = sc.nextInt();W = sc.nextInt();X = sc.nextInt();K = sc.nextInt();sumR = new int[H];sumC = new int[W];arr = new int[H][W];for(int i = 0; i<H; i++) {for(int j = 0; j<W; j++) {arr[i][j] = sc.nextInt();sumR[i]+=arr[i][j];}}for(int j = 0; j<W; j++) {for(int i = 0; i<H; i++) {sumC[j] +=arr[i][j];}}}public int getMin(int[] a) {int min=0;for(int i=1; i<a.length; i++) {if(a[min]>a[i]) min = i;}return min;}public void solve() {for(int temp = 0; temp<K&&temp<(W+H); temp++) {int minSumR = getMin(sumR);int minSumC = getMin(sumC);if((W*X-sumR[minSumR])>=(H*X-sumC[minSumC])&&((W*X-sumR[minSumR])>0)) {for(int j = 0; j<W; j++) {sumC[j] = sumC[j]-arr[minSumR][j]+X;arr[minSumR][j] = X;}sumR[minSumR] = W*X;} else if((W*X-sumR[minSumR])<=(H*X-sumC[minSumC])&&((H*X-sumC[minSumC])>0)) {for(int i=0; i<H; i++ ){sumR[i] = sumR[i]-arr[i][minSumC]+X;arr[i][minSumC] = X;}sumC[minSumC] = H*X;}}int sum = 0;for(int i= 0; i<H; i++) {sum+=sumR[i];}for(int i = 0; i<H; i++) {for(int j = 0; j<W; j++) {System.out.print(arr[i][j]+" ");}System.out.println();}System.out.println(sum);}public static void main(String[] args) {Main m = new Main();m.solve();}}

跑出来,第一个例子不对。死活找不到原因。

大神给举例:

3

2

3

2

-100 -100

-1   -1

-1   -1

按照我的想法,跑出来是10

但是实际上可以有

3   3

3   3

3   3

输出是18。


修改后代码如下:

package Indeed;import java.util.ArrayList;import java.util.Collections;import java.util.List;import java.util.Scanner;public class Third {private  int[] arr = {0,1,2,3,4,5,6,7,8,9};private int k;private int col;private int[][] nums;private int[] sumC;private int x;private int max;private int changeNums;public  Third(int H, int W,int X,int changeNums,int[][] nums) {this.k = H;this.col = W;this.nums = nums;this.x = X;this.changeNums = changeNums;sumC = new int[col];for(int j = 0; j<col; j++) sumC[j] = 0;}public int solve() {int max = Integer.MIN_VALUE;for(int i = 0; i<(1<<k); i++) {int n=0;for (int j=0;j<k;j++)if(((i>>j)&1)==1)n++;int length =changeNums-n;if(length<0) continue;int[][] numsAfter = nums;for (int j=0;j<k;j++)if(((i>>j)&1)==1)for ( int l = 0 ; l < col ; l ++ )numsAfter[j][l] = x ;for(int j = 0; j<col;j++) {sumC[j] = 0;for(int t = 0; t<k; t++) {sumC[j]+=numsAfter[t][j];}}sort(sumC);for(int t = 0; t<col&&t<length&&sumC[t]<k*x;t++) {sumC[t] = k*x;}int result = 0;for(int t = 0; t<col; t++) {result+=sumC[t];}if(i==120) {for(int row = 0; row<k; row++) {for(int j = 0;j<col; j++) {System.out.print(numsAfter[row][j]+" ");}System.out.println();}System.out.println(result+"  max:"+max);}max = Math.max(max, result);}return max;}public void sort(int[] a) {for(int i = 0; i<a.length; i++) {for(int j = i; j<a.length; j++) {if(a[i]>a[j]) {int temp = a[j];a[j] = a[i];a[i] = temp;}}}}public static void main(String[] args) {Scanner sc = new Scanner(System.in);int H = sc.nextInt();int W = sc.nextInt();int x = sc.nextInt();int k = sc.nextInt();int[][] nums = new int[H][W];for(int i = 0; i<H; i++) {for(int j = 0; j<W; j++) {nums[i][j] = sc.nextInt();}}Third th = new Third(H,W,x,k,nums);System.out.println(th.solve());}}

嗯。还是错了。大神帮忙找原因。

原因找到。

主要有两个原因。

1、int[] a = new int[2][3];

      int[] b = a;

      b[1] =2;

     a的大小也会随着b的大小的改变而改变,

因此 代码里的 numsAfter = nums  应该改成每一个数字进行赋值。

2、sort排序。

sort是对整个sumC数组进行的排序。但是实际上 sumC数组里面只有前col个有数据,剩余部分的数据都是之前的数据未清除。所以应是对前col个数据进行排序。然后同样只计算前col个数据的和。

修改后的代码如下:

package Indeed;import java.util.ArrayList;import java.util.Collections;import java.util.List;import java.util.Scanner;public class Third {private  int[] arr = {0,1,2,3,4,5,6,7,8,9};private int k;private int col;private static  int[][] nums = new int[10][200];private int[] sumC = new int[200];private int x;private int max;private int changeNums;public  Third() {Scanner sc = new Scanner(System.in);k = sc.nextInt();col = sc.nextInt();x = sc.nextInt();changeNums = sc.nextInt();for(int i = 0; i<k; i++) {for(int j = 0; j<col; j++) {nums[i][j] = sc.nextInt();}}}public int solve() {int max = Integer.MIN_VALUE;for(int i = 0; i<(1<<k); i++) {int n=0;for (int j=0;j<k;j++)if(((i>>j)&1)==1)n++;int length =changeNums-n;if(length<0) continue;int[][] numsAfter = new int[k][col];for(int l = 0; l<k; l++) {for(int t = 0; t<col; t++) {numsAfter[l][t] = nums[l][t];}}for (int j=0;j<k;j++)if(((i>>j)&1)==1)for ( int l = 0 ; l < col ; l ++ )numsAfter[j][l] = x ;for(int j = 0; j<col;j++) {sumC[j] = 0;for(int t = 0; t<k; t++) {sumC[j]+=numsAfter[t][j];}}sort(sumC,0,col);for(int t = 0; t<col&&t<length&&sumC[t]<k*x;t++) {sumC[t] = k*x;}int result = 0;for(int t = 0; t<col; t++) {result+=sumC[t];}max = Math.max(max, result);}return max;}public void sort(int[] a,int start, int end) {for(int i = start; i<end; i++) {for(int j = i; j<end; j++) {if(a[i]>a[j]) {int temp = a[j];a[j] = a[i];a[i] = temp;}}}}public static void main(String[] args) {Third th = new Third();System.out.println(th.solve());}}


整理了下代码:

package Indeed;/* * 882914-89 -76 92 61 5 -18 -68 90-3 44 -9 84 -36 51 -43 8511 -72 5 -90 -43 -94 5 97-90 22 66 29 -26 66 -29 -3882 -60 60 -9 -23 -8 -59 -13-4 -68 -4 59 78 25 99 -86-4 23 21 53 53 -25 -31 -6638 50 -35 -98 -49 -33 -31 88output:21003232-100 -100-1   -1-1   -1output:18 */import java.util.Scanner;public class Main {private int H;private int W;private int X;private int K;private int[][] arr = new int[10][200];private int[][] arrAfter = new int[10][200];public Main() {Scanner sc = new Scanner(System.in);H = sc.nextInt();W = sc.nextInt();X = sc.nextInt();K = sc.nextInt();arr = new int[H][W];for(int i = 0; i<H; i++) {for(int j = 0; j<W; j++) {arr[i][j] = sc.nextInt();}}}public int solve() {int max = Integer.MIN_VALUE;for(int s = 0; s<(1<<H);s++) {int n = 0;int[][] nums = new int[H][W];for(int i = 0; i<H; i++) {for(int j = 0; j<W; j++) {nums[i][j] = arr[i][j];}}for(int j = 0; j<H; j++) {if(((s>>j)&1)==1) {for(int l = 0; l<W; l++) {nums[j][l] = X;}n++;}}int size = K-n;int[] colSum = new int [W];for(int j = 0; j<W; j++) {colSum[j] = 0;for(int i = 0; i<H; i++) {colSum[j]+=nums[i][j];}}sort(colSum,0,W);for(int i = 0; i<size&&i<W&&colSum[i]<H*X; i++) {colSum[i]=H*X;}int result = 0;for(int i = 0; i<W; i++) {result+=colSum[i];}max = Math.max(result, max);}return max;}public void sort(int[] colSum, int start, int end) {for(int i = start; i<end; i++) {for(int j = i; j<end; j++) {if(colSum[i]>colSum[j]) {int temp = colSum[i];colSum[i] = colSum[j];colSum[j] = temp;}}}}public static void main(String[] args) {Main m = new Main();System.out.println(m.solve());}}



0 0
原创粉丝点击