藍橋杯程式設計題——完美的代價——貪心演算法(存在一定問題,希望各路大神糾正一下)
阿新 • • 發佈:2019-02-11
問題描述 迴文串,是一種特殊的字串,它從左往右讀和從右往左讀是一樣的。小龍龍認為迴文串才是完美的。現在給你一個串,它不一定是迴文的,請你計算最少的交換次數使得該串變成一個完美的迴文串。
交換的定義是:交換兩個相鄰的字元
例如mamad
第一次交換 ad : mamda
第二次交換 md : madma
第三次交換 ma : madam (迴文!完美!)輸入格式 第一行是一個整數N,表示接下來的字串的長度(N <= 8000)
第二行是一個字串,長度為N.只包含小寫字母輸出格式 如果可能,輸出最少的交換次數。
否則輸出Impossible樣例輸入5
mamad樣例輸出
交換的定義是:交換兩個相鄰的字元
例如mamad
第一次交換 ad : mamda
第二次交換 md : madma
第三次交換 ma : madam (迴文!完美!)輸入格式 第一行是一個整數N,表示接下來的字串的長度(N <= 8000)
第二行是一個字串,長度為N.只包含小寫字母輸出格式 如果可能,輸出最少的交換次數。
否則輸出Impossible樣例輸入5
mamad樣例輸出
3
本題寫到現在還存在一定問題,希望各路大神糾正一下。
package 貪心演算法; import java.util.Scanner; public class 完美的代價 { public static void main(String[] args) { // TODO 自動生成的方法存根 Scanner input = new Scanner(System.in); int n = input.nextInt(); String s = input.next(); char[] cs = s.toCharArray(); boolean flag = false;//如果n是基數,用flag判斷找到了一個單個字的 int count = 0; int end = n-1; //從0到倒數第二遍歷,再倒著找一樣的 for(int i = 0; i < n - 1 ; i++ ) { for (int j = end; j > i; j--) { if (j==i) { //沒找到 if (n % 2 == 0 || flag) {//不存在的兩種情況 System.out.println("Impossible"); System.exit(0); } else { //把這個字元放到中間去 flag = true; char tmp = cs[i]; cs[i] = cs[n/2]; cs[n/2] = tmp; count += n / 2 - i; break; } } else if (cs[i] == cs[j]) { for (int k = j; k < end; k++) { char tmp = cs[k]; cs[k] = cs[k+1]; cs[k+1] = tmp; count++; } end--; break; } } } if (isHuiWen(cs)) { System.out.println(count); } else { System.out.println("Impossible"); } } public static boolean isHuiWen(char[] s) { String a = String.valueOf(s); String b = new StringBuffer(a).reverse().toString(); return a.equals(b); } }
自我感覺有問題的地方在於,吧單個字元放到中間去的時候,會不會對之後的交換次數產生影響。
還有就是impossible的輸出情況,如果最後在判斷一次是否是迴文數的話,可能並沒有完全交換完。
還有問題可能我沒有發現。。。。歡迎留言。。