2016年6月1日 星期三

UVA 11340 Newspaper (講解fgets)

/*
    題目連結

    為啥我覺得 Competitive Programming上
    滿滿是坑新手的題目啊... 很多處理上很麻煩...

    主要的想法是 char 其實也是一種數字(-128~127)
    (正常字元在 0~127)
    所以我們直接把字元 當陣列的index來
    讀入 查詢數值就好了

    但是這題 它的字元編號居然會 >= 128 (我有驗證過)
    (也就是非正常字元) 用 char 來存會變負的
    所以要 +128 來平移 
    
    另外不會有空白字元 也有稿費的情況 (也有驗證)
    不過文章裡可能會有空行!(我被這個陰了) QAQ
    原本用 scanf("%[^\n]", line); getchar();
    而非 fgets 然後你會發現 空行會導致 %[^\n] 匹配失敗
    然後line 就維持在上一行輸入的情況...

    講一下 fgets()的用法
    因為 gets() 被C++11刪掉了XD
    一般我們拿 fgets() 來讀取一整行的字串 (直到換行字元)
    (不像cin,scanf的一般用法 讀到空白字元就停了)
    第一個參數是 你用來存輸入的變數
    第二個是你最多讓它讀幾個字元 (如果超過 剩下的它不讀)
    第三個是檔案指針 因為我們希望是標準輸入 所以我們丟stdin進去
    
    注意到fgets會把 換行字元'\n'也讀進來  
    要小心~~
*/
#include <iostream>
#include <cstring>
#include <cstdio>

using namespace std;

int val[301];
char line[30001];

void read_to_eol()
{
    while(1)
    {
        char c = getchar();
        if( c == '\n' ) break;
    }
}

int main()
{
    int N;
    scanf("%d", &N);

    while( N-- )
    {
        memset(val, 0, sizeof(val));

        int K;
        scanf("%d", &K);
        read_to_eol();

        for(int Ki = 0; Ki < K; Ki++)
        {
            char c;
            scanf("%c", &c);
            scanf("%d", &val[c+128]);
            read_to_eol();
        }

        int ans = 0;

        int M;
        scanf("%d", &M);
        read_to_eol();

        for(int Mi = 0; Mi < M; Mi++)
        {
            fgets(line, 30001, stdin);

            int ln = strlen(line);
            for(int li = 0; li < ln; li++)
                ans += val[line[li]+128 ];
        }

        printf("%d.%02d$\n", ans/100, ans%100);
    }
}

沒有留言:

張貼留言