zoukankan      html  css  js  c++  java
  • leetcode刷题笔记313题 超级丑数

    leetcode刷题笔记313题 超级丑数

    源地址:313. 超级丑数

    问题描述:

    编写一段程序来查找第 n 个超级丑数。

    超级丑数是指其所有质因数都是长度为 k 的质数列表 primes 中的正整数。

    示例:

    输入: n = 12, primes = [2,7,13,19]
    输出: 32
    解释: 给定长度为 4 的质数列表 primes = [2,7,13,19],前 12 个超级丑数序列为:[1,2,4,7,8,13,14,16,19,26,28,32] 。
    说明:

    1 是任何给定 primes 的超级丑数。
    给定 primes 中的数字以升序排列。
    0 < k ≤ 100, 0 < n ≤ 106, 0 < primes[i] < 1000 。
    第 n 个超级丑数确保在 32 位有符整数范围内

    //思路一 通过维护最小堆,将每次可能的结果压入优先队列,将同样的结果从堆中排除, 直到n个元素出队列即可
    import scala.collection.mutable.PriorityQueue
    object Solution {
        def nthSuperUglyNumber(n: Int, primes: Array[Int]): Int = {
           val heap = PriorityQueue.empty[Long](Ordering.by(n => n)).reverse
           var count = n
    
           heap.enqueue(1)
           count -= 1
    
           while (count > 0) {
               val x = heap.dequeue
               while (heap.length > 0 && heap.head == x) {heap.dequeue}
               for (i <- 0 to primes.length-1) { 
                   heap.enqueue(x * primes(i))
                }
               count -= 1
           }
    
           return heap.dequeue.toInt
        }
    }
    
    //基于动态规划 构建dp数组存储丑数序列,index序列存储对应的primes中的质数应该与dp中的那个数求乘积
    //而后记录每次的最小值放入, 注意去除重复值
    object Solution {
        def nthSuperUglyNumber(n: Int, primes: Array[Int]): Int = {
            val dp = Array.fill(n)(0)
            val index = Array.fill(primes.length)(0)
    
            dp(0) = 1
    
            for (i <- 1 to n-1){
                var min = Int.MaxValue
                for (j <- 0 to index.length-1) {
                    if (min > primes(j) * dp(index(j))) {min = primes(j) * dp(index(j))}
                }
                dp(i) = min
                for (j <- 0 to index.length-1) {
                    if (min == primes(j) * dp(index(j))) {index(j) += 1}
                }
            }
    
            return dp(n-1)
        }
    }
    
    //注意go中堆的使用方法
    import "container/heap"
    
    type UglyNums []int
    
    func (u *UglyNums) Push(x interface{}) {
        *u = append(*u, x.(int))
    }
    
    func (u *UglyNums) Pop() interface{} {
        n := len(*u)
        x := (*u)[n-1]
        (*u) = (*u)[0:n-1]
        return x
    }
    
    func (u UglyNums) Len() int {
        return len(u)
    }
    
    func (u UglyNums) Less(i, j int) bool {
        return u[i] < u[j]
    }
    
    func (u UglyNums) Swap(i, j int) {
        u[i], u[j] = u[j], u[i]
    }
    
    func nthSuperUglyNumber(n int, primes []int) int {
        if n == 0 || n == 1 {return n}
        curHeap := new(UglyNums)
        heap.Push(curHeap, 1)
        n--
    
        for (n > 0) {
            x := heap.Pop(curHeap).(int)
            for (curHeap.Len() > 0 && (*curHeap)[0] == x) {heap.Pop(curHeap)}
            for i := 0; i < len(primes); i++ {
                heap.Push(curHeap, x*primes[i])
            }
            n -- 
        }
    
        return heap.Pop(curHeap).(int)
    }
    
    //
    func nthSuperUglyNumber(n int, primes []int) int {
        length := len(primes)
        dp := make([]int, n)
        index := make([]int, length)
    
        dp[0] = 1
    
        for i := 1; i < n; i++ {
            min := math.MaxInt32  
            for j := 0; j < length; j++ {
                if min > primes[j] * dp[index[j]] {min = primes[j] * dp[index[j]]}
            }
            dp[i] = min
            for j := 0; j < length; j++ {
                if min == primes[j] * dp[index[j]] {index[j] += 1}
            } 
        }
        return dp[n-1]
    }
    
  • 相关阅读:
    sql测试
    sql时间和日期函数
    递归算法
    冒泡排序
    Ajax
    省市区下拉框三级联动
    Repeater用法
    WIndows form Linq多表联合
    C# 递归算羊
    C# 定义一个学生的结构体,输入学生信息,学号,姓名,身高,按身高排序输出
  • 原文地址:https://www.cnblogs.com/ganshuoos/p/14087509.html
Copyright © 2011-2022 走看看