简体   繁体   English

数字三角形上非素数的最大和

[英]Max sum of non prime numbers on triangle of numbers

I have a triangle of numbers.我有一个数字三角形。 I want to find the largest sum of the NOT PRIME numbers starting from the top in this triangle.我想从这个三角形的顶部开始找到最大的非素数之和。 For example:例如:

  1. You will start from the top and move downwards to an adjacent number as in below.您将从顶部开始并向下移动到相邻的数字,如下所示。
  2. You are only allowed to walk downwards and diagonally.您只能沿对角线向下走。
  3. You can only walk over NON PRIME NUMBERS.你只能走过非质数。
  4. You have to reach at the end of the pyramid as much as possible.你必须尽可能地到达金字塔的尽头。
  5. You have to treat the input as pyramid.您必须将输入视为金字塔。

According to above rules the maximum sum of the numbers from top to bottom in below example is 24.根据上述规则,下例中从上到下的最大数字总和为 24。

      *1
     *8 4
    2 *6 9
   8 5 *9 3

As you can see this has several paths that fits the rule of NOT PRIME NUMBERS;正如你所看到的,这有几条符合 NOT PRIME NUMBERS 规则的路径; 1>8>6>9, 1>4>6>9, 1>4>9>9 1 + 8 + 6 + 9 = 24. As you see 1, 8, 6, 9 are all NOT PRIME NUMBERS and walking over these yields the maximum sum. 1>8>6>9, 1>4>6>9, 1>4>9>9 1 + 8 + 6 + 9 = 24. 如你所见 1, 8, 6, 9 都不是质数并且走超过这些产生最大的总和。

My code is below.我的代码如下。 My code doesn't consider prime numbers.我的代码不考虑素数。 How can I do it like in the example above?我怎么能像上面的例子那样做呢?

public class MaxPathSum {

    public static void main(String[] args) throws Exception {
        int[][] data = Files.lines(Paths.get("src/main/triangle.txt"))
                .map(s -> stream(s.trim().split("\\s+"))
                        .mapToInt(Integer::parseInt)
                        .toArray())
                .toArray(int[][]::new);

        for (int r = data.length - 1; r > 0; r--)
            for (int c = 0; c < data[r].length - 1; c++)
                data[r - 1][c] += Math.max(data[r][c], data[r][c + 1]);

        System.out.println(data[0][0]);
    }
}

Example data:示例数据:

        1
       8 4
      2 6 9
     8 5 9 3

Somewhere at a value, row r , column c .某处值,行r ,列c You possibly could come from left parent [r-1][c-1] (c > 0) or right parent [r-1][c] (c < r).您可能来自左父母[r-1][c-1] (c > 0) 或右父母[r-1][c] (c < r)。

You stop with failure when the value is a prime.当值是质数时,您会因失败而停止。

Going down in both cases you want the maximum, and with a solution of the subtree.在这两种情况下,您都想要最大值,并使用子树的解决方案。 When failure fail.当失败失败。

So going first down the subtree:所以首先沿着子树走:

record Solution(int sum, List<Integer> path) {}

Optional<Solution> solve(int r, int c) {
    int value = data[r][c];
    if (isPrime(value)) {
        return Optional.empty();
    }
    if (r+1 >= data.length) {
        List<Integer> path = new ArrayList<>();
        path.add(value);
        return Optional.of(new Solution(value, path));
    }
    Solution left = solve(r+1, c);
    Solution right = solve(r+1, c+1);
    if (!left.isPresent()) {
        if (!right.isPresent()) {
            return Optional.empty();
        } else {
            List<Integer> path = left.path;
            path.add(0, value);
            return Optional.of(new Solution(value + left.sum, path));
        }
    } else {
        if (!right.isPresent()) {
            List<Integer> path = right.path;
            path.add(0, value);
            return Optional.of(new Solution(value + right.sum, path));
        } else {
            if (left.sum > right.sum) {
                List<Integer> path = left.path;
                path.add(0, value);
                return Optional.of(new Solution(value + left.sum, path));
            } else {
                List<Integer> path = right.path;
                path.add(0, value);
                return Optional.of(new Solution(value + right.sum, path));
            }
        }
    }
}

Of course you could also work with an int[][] sum at the bottom row filling primes with a -1, and a sum of the two values under when not -1.当然,您也可以在底行使用 int[][] 总和,用 -1 填充素数,如果不是 -1,则使用两个值的总和。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM