• leetcode 1320 二指输入的最小距离


    题目描述:

     

     题解: dp题目,构造一个三维的dp[i][j][k]表示在i位置时,左手在j字母上,右手在k字母上所需要移动的最小次数。

    初始化的时候,dp(0,j,k)=0其他位置为正无穷。

    状态转移方程。 t为word[i]对应的字母。要么左手从位置i-1移动位置到位置i,dp(i,t,k) = min(dp(i,t,k), dp(i-1,j,k)+dis(j,t));

    要么右手从位置i-1移动到位置i,dp(i,j,t) = min(dp(i,j,t), dp(i-1,j,k)+dis(t,k));

    (最开始的时候只想到用位置来建立状态信息,这里用字母来构造状态是比较好的)

    AC代码:

    class Solution {
    public:
        int dis(pair<int,int> a,pair<int,int> b)
        {
            int t1 = a.first - b.first;
            int t2 = a.second - b.second;
            if(t1 < 0) t1 = -1*t1;
            if(t2 < 0) t2 = -1*t2;
            return t1+t2;
        }
        int minimumDistance(string word) {
            map<char,pair<int,int>> mp;
            int i= 0;
            for(char c = 'A'; c<='F';c++)
            {
                mp[c] = make_pair(0,i);
                i++;
            }
            i =0 ;
            for(char c = 'G'; c<='L';c++)
            {
                mp[c] = make_pair(1,i);
                i++;
            }
            i =0 ;
            for(char c = 'M'; c<='R';c++)
            {
                mp[c] = make_pair(2,i);
                i++;
            }
            i =0 ;
            for(char c = 'S'; c<='X';c++)
            {
                mp[c] = make_pair(3,i);
                i++;
            }
             i =0 ;
            for(char c = 'Y'; c<='Z';c++)
            {
                mp[c] = make_pair(4,i);
                i++;
            }
    
            int Len = word.length();
            int dp[Len+10][27][27];
            // 还是三维的好处理一些
            for(int i=0;i<=Len;i++)
            {
                for(int j=0;j<26;j++)
                {
                    for(int k=0;k<26;k++)
                    {
                        if(i == 0) dp[i][j][k] =0;
                        else dp[i][j][k] = INT_MAX;
                    }
                }
            }
            
    
            for(int i=1;i<=Len;i++)
            {
                int t = word[i-1]-'A';
                for(int j=0;j<26;j++)
                {
                    for(int k=0;k<26;k++)
                    {
                        if(dp[i-1][j][k] != INT_MAX)
                        {
                            dp[i][t][k] = min(dp[i][t][k],dp[i-1][j][k]+dis(mp[j+'A'],mp[t+'A']));
                            dp[i][j][t] = min(dp[i][j][t],dp[i-1][j][k]+dis(mp[k+'A'],mp[t+'A']));
                        }
                    }
                }
            }
            int mn = INT_MAX;
            for(int i=0;i<26;i++)
            {
                for(int j=0;j<26;j++) mn = min(mn,dp[Len][i][j]);
            }
    
    
            return mn;
        }
    };
  • 相关阅读:
    结对
    汉堡 结对2.0
    《构建之法》第四章读后感
    复利计算单元测试
    实验一 命令解释程序的编写
    《构建之法》读后感
    复利计算 2.0
    了解和熟悉操作系统
    学习进度条
    perl的贪婪和非贪婪模式
  • 原文地址:https://www.cnblogs.com/z1141000271/p/12188896.html
Copyright © 2020-2023  润新知