zoukankan      html  css  js  c++  java
  • SRM DIV2 572 NextOrPrev

    【题意】将字符串A变成字符串B,两种操作:Next,将字符置换成下一个字符('a'>'b','b'>'c'...'y'>'z');Prev,将字符置换成前一个字符('z'>'y','y'>'x'...'b'>'a')。Next和Prev操作的代价不同,求出最小代价,如果不行则返回-1。

    【算法】:
    1.判断能否由A得到B。如果不能,return -1;
      如何判断:可以建立一个二部图。左右两侧的点依次为a、b、c...y、z。(A[i],B[i])代表二部图中的一条边,任意两条边有相交,则A不能得到B。因此判断条件是(A[i]-A[j])*(B[i]-B[j])不能为负,for any i,j。
    2.计算代价。

    【Java代码】来自菜鸟

     1 import java.util.*;
     2 import java.util.regex.*;
     3 import java.text.*;
     4 import java.math.*;
     5 
     6 
     7 public class NextOrPrev
     8 {
     9     public int getMinimum(int nextCost, int prevCost, String start, String goal)
    10     {
    11         char[] s = start.toCharArray();
    12         char[] g = goal.toCharArray();
    13         
    14         //check if we can get to goal
    15         int i,j;
    16         for(i=0;i<s.length;i++){
    17             for(j=i+1;j<s.length;j++){
    18                 if((s[i]-s[j])*(g[i]-g[j])<0)
    19                     return -1;
    20             }
    21         }
    22         //compute
    23         int count=0;
    24         for(i=0;i<s.length;i++){
    25             if(s[i]<g[i]){
    26                 count+=nextCost*(g[i]-s[i]);
    27             }
    28             else{
    29                 count+=prevCost*(s[i]-g[i]);
    30             }
    31         }
    32         
    33         return count;
    34     }
    35     
    36 
    37 }
    38 //Powered by KawigiEdit 2.1.4 (beta) modified by pivanof!
    View Code

    【Java代码】来自大神

    【分析】他给A[i],B[i]排了序,反映到二部图上来,也是不能有边相交。

    public class NextOrPrev {
     
      public int getMinimum(int nextCost, int prevCost, String start, String goal) {
        int length = start.length();
        int[] alignStart = new int[length];
        int[] alignGoal = new int[length];
        int i;
        int cost = 0;
        
        
        i = 0;
        for(char c = 'a'; c <= 'z'; c++) {
          for(int j=0; j<length; j++) {
            if (start.charAt(j) == c) {
              alignStart[j] = i++;
              break;
            }
          }
        }
     
        i = 0;
        for(char c = 'a'; c <= 'z'; c++) {
          for(int j=0; j<length; j++) {
            if (goal.charAt(j) == c) {
              alignGoal[j] = i++;
              break;
            }
          }
        }
        
        for(int j=0; j<length; j++) {
          int dist;
          
          if(alignStart[j] != alignGoal[j]) {
            return -1;
          }
          dist = start.charAt(j) - goal.charAt(j);
          
          cost += dist < 0 ? nextCost * dist * -1 : prevCost * dist;  
        }
        
        
        
        return cost;
      }
     
    }
    View Code

    【C++代码】来自大神

    【分析】大神的判断条件,在二部图上反映出来也是两条边不能相交。但不知道大神是否也是用二部图来分析的,是否有更好的想法?

    #include<vector>
    #include<string>
    #include<algorithm>
    using namespace std;
     
    class NextOrPrev{
      public:
      int getMinimum(int ne,int pr,string st,string go){
        int i,j,k,n;
        n=st.length();
        for(i=0;i<n;i++)
          for(j=0;j<n;j++)
            if((st[i]<st[j] && go[i]>go[j]) || (st[i]>st[j] && go[i]<go[j]))
              return -1;
        int ans=0;
        for(i=0;i<n;i++)
          if(st[i]<go[i])ans+=(((int)go[i])-((int)st[i]))*ne;
          else ans+=(((int)st[i])-((int)go[i]))*pr;
        return ans;
      }
    };
    View Code

    【总结】:通过看大神的代码,自己YY出来的二部图模型,不知道有没有更好的方法。

  • 相关阅读:
    JavaScript中对事件简单的理解
    正则表达式 RE模块
    模块
    面向对象进阶
    元类详细解释
    四.面向对象和函数补充
    四.函数
    Python的基础知识:
    五层协议及tcp三次握手四次挥手
    nginx常见错误
  • 原文地址:https://www.cnblogs.com/wang3/p/3221993.html
Copyright © 2011-2022 走看看