zoukankan      html  css  js  c++  java
  • [LeetCode 1167] Minimum Cost to Connect Sticks

    You have some sticks with positive integer lengths.

    You can connect any two sticks of lengths X and Y into one stick by paying a cost of X + Y.  You perform this action until there is one stick remaining.

    Return the minimum cost of connecting all the given sticks into one stick in this way.

     

    Example 1:

    Input: sticks = [2,4,3]
    Output: 14
    

    Example 2:

    Input: sticks = [1,8,3,5]
    Output: 30
    

     

    Constraints:

    • 1 <= sticks.length <= 10^4
    • 1 <= sticks[i] <= 10^4

    This is a direct application of the Huffman Coding algorithm. In this problem, each stick's length is the equivalence of character frequency, the goal here is to merge all sticks into one stick with the minimum cost, this is essentially the same with building a Huffman tree with minimum cost. Each merge operation merges two meta-sticks(two subtrees) into one subtree with the introduction of a new internal tree node. The gist of the Huffman Coding is to greedily pick the 2 least frequent characters and merge them, then recursively solve a smaller problem with 1 fewer character. In this problem, this translates into picking the 2 least stick lengths.

    There are two efficient ways of implementing the Huffman Coding algorithm.

    Solution 1. PriorityQueue

    Since we conduct repeated finding minimum operations, PriorityQueue suits well for such application. 

    class Solution {
        public int connectSticks(int[] sticks) {
            PriorityQueue<Integer> minPq = new PriorityQueue<>();
            for(int v : sticks) {
                minPq.add(v);
            }
            int cost = 0;
            while(minPq.size() > 1) {
                int v1 = minPq.poll();
                int v2 = minPq.poll();
                cost += (v1 + v2);
                minPq.add(v1 + v2);
            }
            return cost;
        }
    }

    Solution 2. Sorting + Two Queue

    Alternatively, we can preprocess the input by sorting it, then manage two queues. The first queue initially stores all input. The second queue is used to store all the meta sticks' length after merging operations. As long as there is more than 1 element left in these 2 queues combined, we repeatedly pick the 2 smallest stick lengths and merge them.

    class Solution {
        public int connectSticks(int[] sticks) {
            Arrays.sort(sticks);
            ArrayDeque<Integer> q1 = new ArrayDeque<>();
            ArrayDeque<Integer> q2 = new ArrayDeque<>();
            for(int v : sticks) {
                q1.addLast(v);
            }
            
            int cost = 0;
            while(!(q1.size() == 1 && q2.size() == 0 || q1.size() == 0 && q2.size() == 1)) {
                int c1 = Integer.MAX_VALUE, c2 = Integer.MAX_VALUE;
                if(q1.size() > 0 && (q2.size() == 0 || q1.peekFirst() <= q2.peekFirst())) {
                    c1 = q1.pollFirst();
                }
                else {
                    c1 = q2.pollFirst();
                }
                if(q1.size() > 0 && (q2.size() == 0 || q1.peekFirst() <= q2.peekFirst())) {
                    c2 = q1.pollFirst();
                }
                else {
                    c2 = q2.pollFirst();
                }
                cost += (c1 + c2);
                q2.addLast(c1 + c2);
            }
            return cost;
        }
    }
  • 相关阅读:
    RPC和Socket
    监控与管理dubbo服务
    系统架构
    Spring Web工程web.xml零配置即使用Java Config + Annotation
    Spring Boot 整合 Elasticsearch,实现 function score query 权重分查询
    Zxing 的集成 ---- Maven 对应 Gradle 的写法
    Android SpannableString与SpannableStringBuilder
    Android 仿微信朋友圈9宫格图片展示&多选图片
    AndroidRichText 让Textview轻松的支持富文本(图像ImageSpan、点击效果等等类似QQ微信聊天)
    Android 清除canvas 笔迹代码
  • 原文地址:https://www.cnblogs.com/lz87/p/12231837.html
Copyright © 2011-2022 走看看