亚洲免费在线-亚洲免费在线播放-亚洲免费在线观看-亚洲免费在线观看视频-亚洲免费在线看-亚洲免费在线视频

UESTC1565 Smart Typist

系統 1818 0

UESTC1565 Smart Typist

Time Limit:? 2000 ms ?Memory Limit:? 65536 kB ?Solved:? 10? Tried:? 49

Description

?

The most mysterious organization in Chani is “Related Department”. It is related to almost everything, and has branches almost everywhere. Events always have relation with it. Whenever disasters happen, “Related Department” would stand out to commit its responsibility. The members of “Related Department” are called “Related person”. However, ordinary people have no idea about who is “Related person” since their information is national secret.
Xiaoming is the top typist in Chani. The legend is that he could type 400 words per minute. Today he accepted an order from a man who said that he is a “Related person”. That “Related person” asked Xiaoming to turn many paper documents into electronic files. For reasons of security, Xiaoming has to use a special device which has limited functions. With the special device, Xiaoming can only perform such operations:
1. Creating a new file. It takes a quite short time that we ignore the time for it.
2. Replacing current file with some file finished before. A file is allowed to be used to replace another one only after it is finished and won’t be edited later.
3. Deleting any letter(s) in current file.
4. Inserting letter(s) at arbitrary position in current file.
Note that, the keyboard for this device is so strange that the time for typing different letter may be different.
Xiaoming is somewhat afraid of dealing with “Related person”, so he wants to accomplish this order as soon as possible. Knowing time needed for each operation, Xiaoming is trying to make the best plan which spends the minimum time.

?

Input

?


The first line of the input is T (no more than 50), which stands for the number of test cases you need to solve.
Each case begins with two integers, repCost and delCost (1 <= repCost, delCost <= 50), time needed to replace current file, time for deleting one letter. On the second line, there are 26 numbers representing the time for typing each letter from ‘a’ to ‘z’, each number is between 1 and 50.
Then a line with an integer N (1 <= N <= 50) is given indicating the number of files.
N lines followed. Each line gives a string only consisting of letters ‘a’-‘z’ to represent a file. The maximum length of the strings is not greater than 50.

?

Output

?


For every test case, you should output "Case #k: c" first in a line, where k indicates the case number and counts from 1, c is the minimum time needed.

?

Simple Input

?

2
1 1
1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
2
aaab
aaaa
10 10
1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
2
aaab
aaaa

?

Simple Output

?

Case #1: 7
Case #2: 8

**************************************************************

題目大意:某個打字員要打n個字符串,有如下操作:

  1.創建一個一個文件,不計時間。

  2.用一個已經存在的文件替換當前文件,花費為rep

  3.刪除某些字符,每刪除一個字符的花費為del

  4.在當前文件任意位置增加字符,花費為val[字符]。

求打完這些字符串所要的最小花費。

解題思路:這道題,怎么說呢。我們把每個字符串當一個節點,一個字符串到另一個字符串的變化花費計算出來,然后再有一個最終節點連到所有的字符串,權值為打這個字符串的花費。那么,問題轉化為這個有向圖中的最小樹形圖。建圖很簡單,求最小樹形圖也不過是套用朱劉算法的模板,然而令人糾結的是怎么把一個字符串變化到另一個字符串的花費,要不是這個,我也不會寫這道題。這個花費很難算啊,經過我、YYB、ZYC一個晚上的思考,終于相處了這個dp過程,真是艱辛苦楚。

直接考慮s1變化到s2的dp:

dp[0][1~len1]=del*len1代表全部刪除,以后一個一個匹配進來。

dp[i][0]=dp[i-1][0]+val[i];

dp[i][j],當s1的第i個==s2的第j個字母,dp[i][j]=dp[i-1][j-1]-del;當s1的第i個!=s2的第j個字母,dp[i][j]=min(dp[i][j-1],dp[i-1][j]+val[i]);

dp很難想 真心的。

        //#pragma comment(linker, "/STACK:65536000")

#include <map>

#include <stack>

#include <queue>

#include <math.h>

#include <vector>

#include <string>

#include <fstream>

#include <stdio.h>

#include <string.h>

#include <stdlib.h>

#include <iostream>

#include <algorithm>

#define N 55

#define M 30

#define E

#define inf 0x3f3f3f3f

#define dinf 1e10

#define linf (LL)1<<60

#define eps 1e-8

#define LL long long

#define clr(a,b) memset(a,b,sizeof(a))

#define D(a) ((a)*(a))

using namespace std;



int n;

int del,rep,val[M],gra[N][N];

string s[N];

int dp[N][N];

int pre[N],vis[N],cnt,ced[N];//ced數組用來縮點用的



void dpt(int a,int b)

{

    string s1=s[a],s2=s[b];

	int len1=s1.size(),len2=s2.size();

	for(int i=0;i<=len1;i++)dp[0][i]=len1*del;

	for(int i=1;i<=len2;i++)

    {

        dp[i][0]=dp[i-1][0]+val[s2[i-1]-'a'];

        for(int j=1;j<=len1;j++)

            if(s1[j-1]==s2[i-1])

                dp[i][j]=dp[i-1][j-1]-del;

            else

                dp[i][j]=min(dp[i][j-1],dp[i-1][j]+val[s2[i-1]-'a']);

    }

    gra[a][b]=dp[len2][len1]+rep;

}



void dfs(int s)//dfs判是否有解

{

    vis[s]=1;cnt++;

    for(int i=1;i<=n;i++)

        if(gra[s][i]<dinf&&!vis[i])

            dfs(i);

}



int ZHULIU(void)

{

    clr(ced,0);int ans=0;

    int i,j,k;

    do

    {

        for(i=2;i<=n;i++)//清除自環,以及求每個點的入邊

        {

            if(ced[i])continue;

            pre[i]=1;

            for(j=2;j<=n;j++)

                if(j!=i&&!ced[j]&&gra[pre[i]][i]>gra[j][i])

                    pre[i]=j;

        }

        for(i=2;i<=n;i++)

        {

            if(ced[i])continue;

            clr(vis,0);

            for(j=i;j!=1&&!vis[j];j=pre[j])vis[j]=1;//尋找環,被vis標記的是環內的點

            if(j==1)continue;

            ans+=gra[pre[j]][j];

            for(i=pre[j];i!=j;i=pre[i])//把環里的權值加到ans中去

                ans+=gra[pre[i]][i],ced[i]=1;

            for(k=1;k<=n;k++)//這個和下面那個for在縮點

                if(!ced[k]&&gra[k][j]<inf)

                    gra[k][j]-=gra[pre[j]][j];

            for(i=pre[j];i!=j;i=pre[i])

                for(k=1;k<=n;k++)

                {

                    if(ced[k])continue;

                    gra[j][k]=min(gra[j][k],gra[i][k]);

                    if(gra[k][i]<inf)

                        gra[k][j]=min(gra[k][j],gra[k][i]-gra[pre[i]][i]);

                }

            break;

        }

    }while(i<=n);

    for(int i=2;i<=n;i++)//把不是剩下的入邊都加上

        if(!ced[i])ans+=gra[pre[i]][i];

    return ans;

}



void re(void)

{

	cin>>rep>>del;

	for(int i=0;i<26;i++)cin>>val[i];

	cin>>n;n++;

	for(int i=2;i<=n;i++)

        cin>>s[i];

}



void run(void)

{

	for(int i=2;i<=n;i++)

        for(int j=2;j<=n;j++)

            gra[i][j]=inf;

    for(int i=2;i<=n;i++)

        for(int j=2;j<=n;j++)

            if(i!=j)

                dpt(i,j);

    for(int i=2;i<=n;i++)

    {

        int a=0,len=s[i].size();

        for(int j=0;j<len;j++)a+=val[s[i][j]-'a'];

        gra[1][i]=a;

    }

    cout<<ZHULIU()<<endl;

}



int main()

{

    //freopen("d:\\in.txt","r",stdin);

	int ncase;

	scanf("%d",&ncase);

	for(int i=1;i<=ncase;i++)

	{

		re();

		cout<<"Case #"<<i<<": ";

		run();

	}

	return 0;

}


      

UESTC1565 Smart Typist


更多文章、技術交流、商務合作、聯系博主

微信掃碼或搜索:z360901061

微信掃一掃加我為好友

QQ號聯系: 360901061

您的支持是博主寫作最大的動力,如果您喜歡我的文章,感覺我的文章對您有幫助,請用微信掃描下面二維碼支持博主2元、5元、10元、20元等您想捐的金額吧,狠狠點擊下面給點支持吧,站長非常感激您!手機微信長按不能支付解決辦法:請將微信支付二維碼保存到相冊,切換到微信,然后點擊微信右上角掃一掃功能,選擇支付二維碼完成支付。

【本文對您有幫助就好】

您的支持是博主寫作最大的動力,如果您喜歡我的文章,感覺我的文章對您有幫助,請用微信掃描上面二維碼支持博主2元、5元、10元、自定義金額等您想捐的金額吧,站長會非常 感謝您的哦!!!

發表我的評論
最新評論 總共0條評論
主站蜘蛛池模板: 香蕉视频禁止18 | 国产精品嫩草影院99av视频 | 久久草视频 | 欧美在线视频免费 | 国产视频中文字幕 | 日日噜噜夜夜狠狠视频buoke | 亚洲精品www久久久久久久软件 | 一级片短视频 | 久久久精品影院 | 91免费精品国自产拍在线不卡 | 免费永久国产在线视频 | 成人毛片免费观看视频在线 | 天天操夜夜操狠狠操 | 夜夜嗷| 久艹视频在线 | 毛片色| 在线亚洲一区二区 | 欧美人交性视频在线香蕉 | 99热这就是里面只有精品 | 99视频福利 | 羞羞视频免费网站 | 香蕉伊人久久 | 欧美久久一区二区 | 亚洲午夜视频 | 亚洲欧美不卡 | 国产日韩视频 | 四虎影视紧急入口地址大全 | 国产高清美女一级a毛片久久w | 精品久久久久久久久久香蕉 | 国产精品久久久久三级 | 亚洲a成人 | 91视频免费观看高清观看完整 | 久久精品视频免费观看 | 亚洲国产精品久久久久网站 | 特级黄毛片 | 久热这里只有精品视频6 | 国产福利在线观看 | 不卡在线视频 | 高清欧美色欧美综合网站 | 久色精品| 亚洲悠悠色综合中文字幕 |