• 网易2017秋招笔试题3:最长公共子括号序列长度


    【问题来源】网传的2017网易秋招笔试题

    【问题描述】

    【算法思路】

     下面的解题思路摘自  http://www.cnblogs.com/Atanisi/p/7500186.html

    刚看到题我就想到暴力解,深搜出所有合法的括号序列,再依次比较公共子序列的长度,返回最长的。但是深搜一般和路径有关,这道题仅仅需要最大公共子序列的长度。而我们发现最大公共子序列的长度就是 s.size() - 1(当且仅当修改距离为 1 时 LCS 最大), 那么我们就想到,可以变换 s 中一个括号的位置,枚举所有的最大公共子序列长度的序列,只是需要判断是否合法。注意到,深搜是枚举所有合法的相同长度的序列,然后我们再在这个集合中去最长的。而后一种思路是我们枚举所有最长公共子序列的序列,然后再在这个集合中去掉非法的和重复的。

    因为是 s, t 长度相同,并且 t 也是合法的括号序列,所以正反括号数跟原来一样。考虑在原序列上枚举一个字符,把这个插入依次到序列的某个位置去,其他序列相对顺序不变,,这样就可以让LCS最大,然后我们判断一下是否合法(这里有个小技巧),去重就用 set。

    【代码】

     1 #include <iostream>
     2 #include <string>
     3 using namespace std;
     4 
     5 int main() {
     6     string s;
     7     cin >> s;
     8     set<string> m;
     9     int n = s.size();
    10     for (int i = 0; i < n; ++i) {
    11         string w = s.substr(0, i) + s.substr(i + 1);
    12         for (int j = 0; j < n - 1; ++j) {
    13             string tmp = w.substr(0, j) + s[i] + w.substr(j);
    14             int num = 0;
    15             for (int k = 0; k < n; ++k) {
    16                 num += (tmp[k] == '(' ? 1 : -1);
    17                 if (num < 0)
    18                     break;
    19             }
    20             if (num >= 0)
    21                 m.insert(tmp);
    22         }
    23     }
    24     cout << (int)m.size() - 1 << endl;
    25 
    26     return 0;
    27 }
  • 相关阅读:
    队列
    StringBuilder&StringBuffer 源码阅读
    八种基本类型的包装类
    Object 源码阅读
    String 类源码分析
    SpringBoot 启动流程
    BeanDefinition 实例化过程
    BeanDefinition 解析流程【解析所有配置类】
    BeanDefinition 实例
    切面触发过程
  • 原文地址:https://www.cnblogs.com/JesusAlone/p/7536149.html
Copyright © 2020-2023  润新知