24h購物| | PChome| 登入
2013-06-05 10:50:27| 人氣775| 回應0 | 上一篇 | 下一篇

[UVA][greedy] 12261 - High Score

推薦 0 收藏 0 轉貼0 訂閱站台

C  High Score

You've just been playing a video game in which you had to move a wormthrough a maze using a joystick. You got the high score, and now youhave to enter your name using this joystick. This works as follows.The initial name displayed on the screen is a string consisting onlyof `A' characters. Initially the first letter of the string isselected. When you move the joystick forward, the selected letter ischanged to the letter that immediately follows it in the alphabet. When you move thejoystick backward, the selected letter is changed to the letter that immediatelyprecedes it in the alphabet. The alphabet wraps around, so the letter following `Z'is `A' and the letter preceding `A' is `Z'.Moving the joystick left or right changes the selection one step tothe left or right, respectively. The selection also wraps around, somoving left when the first letter is selected will select the lastletter and vice versa.Because you would like to spend as little time as possible on enteringyour name, you want to know the smallest possible number of joystickmoves needed to do this. Given the name you want to enter, write aprogram that calculates the minimum number of moves needed. You mayassume that the length of the initial string is the same as the length of the namethat you want to enter. Furthermore, it does not matter which letteris selected at the end of the process.

Input

On the first line a positive integer: the number of test cases, atmost 100. After that per test case:
  • One line with a string s (1 ≤ length(s) ≤ 1 000) consisting of uppercase letters: the name that you want toenter.

Output

Per test case:
  • One line with an integer: the minimum number of joystick movesneeded.

Sample in- and output

Input Output
2
JEROEN
JAN
56
23


題目描述:
在遊戲設定自己的名稱時,預設欄位全部都是 'A',然後當前位置在最左邊,使用方向鍵將其轉換成目標名字,往前往後,可將當前位置的字元往前移動或者往後移動(這裡是環狀的 'A'-'Z'),往左往右則是換下一個字元修改(位置也是環狀的,往左會繞到最右邊),最後停留的位置不限。
問最少操作次數為何?

題目解法:

基本上,修改字元跟移動位置兩者不相干,而且經過某個位置一定會做調整到正確字元。
那麼題目就轉換成用最少步數覆蓋要修改的位置。
分成四種可能去考慮。
 1 是要修改的,其餘是不用修改的,即目標名字的這個位置是 'A'

1) 一路到最右邊要修改的
....1.....1 .... 1 ... 1 ...
>>>>>>>>>>>>>>>>>>>>>>>>

2) 一路到最左邊要修改的
....1.....1 .... 1 ... 1 ...
<   <<<<<<<<<<<<<<<<<<<<<<<<

3) 曲折先往右在往左
,找任意相鄰要修改的進行這個動作
....1.....1 ....  .... 1....1...1...
>>>>>>>>>>>>>>>>>>>>>>>>
<<<<<<<<<<<<<<<<<<<<<<<<    <<<<<<<<


4) 曲折先往左在往右
,找任意相鄰要修改的進行這個動作
....1.....1 ....  .... 1....1...1...
<                           <<<<<<<<
>>>>>>>>>>>>>>>>>>>>>>>>    >>>>>>>>


#include <stdio.h>
#include <algorithm>
#include <string.h>
using namespace std;
int main() {
    /*freopen("in.txt", "r+t", stdin);
    freopen("out2.txt", "w+t", stdout);*/
    int testcase;
    char s[1005];
    int cost[1005];
    scanf("%d", &testcase);
    while(testcase--) {
        scanf("%s", s);
        int n = strlen(s);
        int ret = 0, dp = 0;
        int i, j, k;
        for(i = 0; i < n; i++) {
            cost[i] = min(s[i]-'A', 26-(s[i]-'A'));
            ret += cost[i];
        }
        if(ret == 0) {
            puts("0");
            continue;
        }
        int pre = -1, count = 0;
        for(i = 0; i < n; i++) {
            if(cost[i]) {
                count ++;
                if(pre == -1)   {
                    pre = i;
                    dp = n-i;
                } else {
                    if(dp == 0) dp = 0xfffffff;
                    dp = min(dp, pre+pre + n-i);
                    dp = min(dp, n-i+n-i + pre);
                    pre = i;
                }
            }
        }
        if(count == 1)  dp = min(pre, n-pre);
        dp = min(dp, pre);
        printf("%d\n", ret + dp);
    }
    return 0;
}

台長: Morris
人氣(775) | 回應(0)| 推薦 (0)| 收藏 (0)| 轉寄
全站分類: 不分類 | 個人分類: UVA |
此分類下一篇:[UVA][積分] 10124 - Subway
此分類上一篇:[UVA][循環] 12464 - Professor Lazy, Ph.D.

是 (若未登入"個人新聞台帳號"則看不到回覆唷!)
* 請輸入識別碼:
請輸入圖片中算式的結果(可能為0) 
(有*為必填)
TOP
詳全文