思路1:
暴力解。dfs,每次如果A[i] > A[i - 1]并且B[i] > B[i - 1],则继续调用;如果A[i] > B[i - 1] 并且 B[i] > A[i - 1] 则说明交换后也可以满足条件,交换然后继续调用。不断update global variable。会TLE。
class Solution { TLE int res = Integer.MAX_VALUE; public int minSwap(int[] A, int[] B) { helper(1, A, B, 0); return res; } private void helper(int s, int[] A, int[] B, int count) { if (s == A.length) { res = Math.min(res, count); return; } if (A[s] >= B[s - 1] && B[s] >= A[s - 1]) { swap(A, B, s); helper(s + 1, A, B, count + 1); swap(A, B, s); } if (A[s] > A[s - 1] && B[s] > B[s - 1]) { helper(s + 1, A, B, count); } } private void swap(int[] A, int[] B, int i) { int temp = A[i]; A[i] = B[i]; B[i] = temp; } }
思路2:
大家都会想到dp, 但是不知道怎么写转移方程。更具体些,其实是不知道判断i时候,i-1位到底换了没换,而且dp本身是不swap来swap去的,不能像dfs那样换了然后继续。于是我们需要把两种情况分开应对。int[] keep表示当前位置不会交换,然后使得满足条件的交换次数;int[] swap表示当前位置会交换,然后使得满足条件的交换次数。依然是思路1的两个branch分别应对即可。
class Solution { // 12 ms public int minSwap(int[] A, int[] B) { int[] swap = new int[A.length]; // swap[i]: must swap index i int[] keep = new int[A.length]; // keep[i]: must keep index i swap[0] = 1; keep[0] = 0; for (int i = 1; i < A.length; i++) { swap[i] = Integer.MAX_VALUE; keep[i] = Integer.MAX_VALUE; if (A[i] > A[i - 1] && B[i] > B[i - 1]) { keep[i] = keep[i - 1]; swap[i] = swap[i - 1] + 1; } if (A[i] > B[i - 1] && B[i] > A[i - 1]) { keep[i] = Math.min(keep[i], swap[i - 1]); swap[i] = Math.min(swap[i], keep[i - 1] + 1); } } return Math.min(keep[A.length - 1], swap[A.length - 1]); } }