【问题标题】:Scala - fill Seq with random numbers, without duplicates and always with same sizeScala - 用随机数填充 Seq,没有重复,并且始终具有相同的大小
【发布时间】:2019-11-05 04:37:07
【问题描述】:

我想创建一个大小始终等于 3 的 IntsSeq。如果一个数字介于 0 到 10 之间,那么我想始终返回一个具有 3 个相同数字的 Seq。如果数字来自其他范围,那么我想返回 3 个随机数的 Seq,但没有重复。我为此创建了一个代码:

object Simulator {
  def toSeq(value: => Int): Seq[Int] = Seq.fill(3)(value)

  def shuffle(): Seq[Int] = {
    val seq = 0 to 100
    val number = Random.nextInt(seq.length)
    number match {
      case _ if 0 to 10 contains number => toSeq(number)
      case _ => toSeq(Random.nextInt(seq.count(_ != number)))
    }
  }
}

但在第二种情况下,我可以随机化 1、2 或 3 个相同的数字,然后我的 Seq 的大小为 1 或 2(删除重复项后)。如何将此代码更改为类似但始终返回长度为 3 的 Seq

【问题讨论】:

    标签: scala random


    【解决方案1】:
    def shuffle(): Seq[Int] = {
      val nums = util.Random.shuffle(Seq.tabulate(101)(identity))
      if (nums.head < 11) Seq.fill(3)(nums.head)
      else nums.take(3)
    }
    

    注意:如果第一个数字超出 0 到 10 的范围,则第二个和/或第三个数字仍然仅限于 0 到 100 的范围。

    【讨论】:

      【解决方案2】:

      这是一种递归方法:

      def threeRands(n : Int, acc : Seq[Int] = Seq()) : Seq[Int] = {
        val num = Random.nextInt(n)
        if(n <= 0) Seq.fill(3)(-1)
        else if(n > 0  && n < 11) {
          Seq.fill(3)(num)
        } else {
          if(acc.size==3) acc
          else if(acc.contains(num)) threeRands(n, acc)
          else threeRands(n, acc :+ num)
        }
      }
      
      threeRands(4) //res0: Seq[Int] = List(1, 1, 1)
      threeRands(13) //res1: Seq[Int] = List(9, 3, 4)
      threeRands(1000) //res2: res2: Seq[Int] = List(799, 227, 668)
      

      这可以通过提取&lt; 11 大小写或使用Set 而不是Seq 来进一步优化。请注意,如果序列的大小远大于 3,这可能需要很长时间,因此最好添加另一个变量来跟踪试验次数以获得所需长度的序列。

      【讨论】:

        猜你喜欢
        • 2013-01-08
        • 2020-07-19
        • 2015-07-28
        • 2018-01-22
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2021-06-24
        相关资源
        最近更新 更多