zoukankan      html  css  js  c++  java
  • 241. 为运算表达式设计优先级(递归)

    1. 题目

    给定一个含有数字和运算符的字符串,为表达式添加括号,改变其运算优先级以求出不同的结果。你需要给出所有可能的组合的结果。有效的运算符号包含 +, - 以及 * 。

    来源:力扣(LeetCode)
    链接:https://leetcode-cn.com/problems/different-ways-to-add-parentheses
    著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

    2. 示例

    输入: "2-1-1"

    输出: [0, 2] 解释: ((2-1)-1) = 0 (2-(1-1)) = 2

    3.题解

    一看到题就觉得有点复杂,可以考虑一下递归的方式,去寻找子问题和原问题解的关系。

    可以通过运算符把整个式子分成两部分,两部分再利用递归解决。

    以 2 * 3 - 4 * 5 为例。

    2 和 3 - 4 * 5 两部分,中间是 * 号相连。

    2 * 3 和 4 * 5 两部分,中间是 - 号相连。

    2 * 3 - 4 和 5 两部分,中间是 * 号相连。

    有了两部分的结果,然后再通过中间的符号两两计算加入到最终的结果中即可。

    比如第一种情况,2 和 3 - 4 * 5 两部分,中间是 * 号相连。

    2 的解就是 [2],3 - 4 * 5 的解就是 [-5, -17]。

    把两部分解通过 * 号计算,最终结果就是 [-10, -34]。

    另外两种情况也类似。

    然后还需要递归出口。

    如果给定的字符串只有数字,没有运算符,那结果就是给定的字符串转为数字。

    比如上边的第一种情况,2 的解就是 [2]。

    4. Code

     1 public class DiffWaysToCompute {
     2     public List<Integer> diffWaysToCompute(String input) {
     3         /**
     4          * @Method: diffWaysToCompute
     5          * @Author: haifwu
     6          * @Version:  1.0
     7          * @Date: 27/05/2021 21:45
     8          * @param input
     9          * @Return: java.util.List<java.lang.Integer>
    10          * @Description: 递归
    11          *
    12          * 题解:
    13          * 以字符为分隔
    14          * 左边的再次进入递归
    15          * 右边进入递归
    16          */
    17         if(input == null || input.length() == 0) {
    18             return new ArrayList<>();
    19         }
    20         List<Integer> result = new ArrayList<>();
    21         int num = 0;
    22         // 考虑是全数字
    23         int index = 0;
    24         while(index < input.length() && !isOperation(input.charAt(index))) {
    25             num = num * 10 + input.charAt(index) - '0';
    26             index++;
    27         }
    28         // 将全数字的情况直接返回
    29         if(index == input.length()) {
    30             result.add(num);
    31             return result;
    32         }
    33         for(int i = 0; i < input.length(); i++) {
    34             if(isOperation(input.charAt(i))) {
    35                 List<Integer> results1 = diffWaysToCompute(input.substring(0, i));
    36                 List<Integer> results2 = diffWaysToCompute(input.substring(i+1));
    37                 for(int j = 0; j < results1.size(); j++) {
    38                     for(int k = 0; k <results2.size(); k++) {
    39                         char op = input.charAt(i);
    40                         result.add(cacultter(results1.get(j), op, results2.get(k)));
    41                     }
    42                 }
    43 
    44             }
    45         }
    46         return result;
    47     }
    48 
    49     private int cacultter(int num1, char c, int num2) {
    50         switch (c) {
    51             case '+':
    52                 return num1 + num2;
    53             case '-':
    54                 return num1 - num2;
    55             case '*':
    56                 return num1 * num2;
    57         }
    58         return -1;
    59     }
    60 
    61     private boolean isOperation(char c) {
    62         return c == '+' || c == '-' || c =='*';
    63     }
    64 
    65     public static void main(String[] args) {
    66         String input = "2-1-1";
    67         System.out.println(new DiffWaysToCompute().diffWaysToCompute(input).toString());
    68     }
    69 }
  • 相关阅读:
    luoguP3181 [HAOI2016]找相同字符
    luoguP4248 [AHOI2013]差异
    luoguP2852 [USACO06DEC]Milk Patterns
    后缀自动机
    luoguP3975 [TJOI2015]弦论
    luoguP2824 [HEOI2016/TJOI2016]排序(线段树分裂做法)
    组合数学学习笔记
    「题解」:[BZOJ2938]病毒 (AC自动机+dfs)
    Linux新人报到
    指针学习笔记
  • 原文地址:https://www.cnblogs.com/haifwu/p/14819949.html
Copyright © 2011-2022 走看看