【问题标题】:Find product of every digit in the given number查找给定数字中每个数字的乘积
【发布时间】:2020-01-08 19:01:49
【问题描述】:

在 scala 中,我需要编写一个方法来查找给定数字中每个数字的乘积。我有以下sn-p。

  def productDigits(number: Int): Int = {
    def helper(current: Int, accumulator: Int): Int = {
      current match {
        case current if current < 10 => accumulator * current
        case _ => helper(current / 10, accumulator * (current % 10))
      }
    }
    helper(number, 1)
  }

有没有更好的办法?

【问题讨论】:

  • number.toString.map(_.toInt),product 如果你想要一个单行,或者如果你的原始号码首先被读取为字符串。但是,你的可能更有效(如果你已经有一个Int
  • @LuisMiguelMejíaSuárez 单行似乎有一个错误,应该是asDigit 而不是toInt :)

标签: scala numbers product digits


【解决方案1】:

这是 OP 的递归解决方案与 Luis 的单线解决方案的 jmh 基准。

执行

sbt "jmh:run -i 10 -wi 10 -f 2 -t 1 bench.So59652263"

在哪里

@State(Scope.Benchmark)
@BenchmarkMode(Array(Mode.Throughput))
class So59652263 {
  def _dexter2305(number: Int): Int = {
    def helper(current: Int, accumulator: Int): Int = {
      current match {
        case current if current < 10 => accumulator * current
        case _ => helper(current / 10, accumulator * (current % 10))
      }
    }
    helper(number, 1)
  }

  def _luis(number: Int): Int = number.toString.map(_.asDigit).product

  val num: Int = (math.random * 100000000).toInt
  @Benchmark def dexter2305: Int = _dexter2305(num)
  @Benchmark def luis: Int = _luis(num)
}

给予

[info] So59652263.dexter2305  thrpt   20  89093066.408 ± 1825286.801  ops/s
[info] So59652263.luis        thrpt   20  11585098.230 ±  272966.526  ops/s

我们看到递归解决方案的吞吐量似乎是单线解决方案的 7 倍。


numberString 而不是Int 时进行基准测试

@State(Scope.Benchmark)
@BenchmarkMode(Array(Mode.Throughput))
class So59652263 {
  def _dexter2305(number: String): Int = {
    def helper(current: Int, accumulator: Int): Int = {
      current match {
        case current if current < 10 => accumulator * current
        case _ => helper(current / 10, accumulator * (current % 10))
      }
    }
    helper(number.toInt, 1)
  }

  def _luis(number: String): Int = number.map(_.asDigit).product

  val num: String = (math.random * 100000000).toInt.toString
  @Benchmark def dexter2305: Int = _dexter2305(num)
  @Benchmark def luis: Int = _luis(num)
}

给予

[info] Benchmark               Mode  Cnt         Score         Error  Units
[info] So59652263.dexter2305  thrpt   20  36237007.844 ± 1631349.975  ops/s
[info] So59652263.luis        thrpt   20  13975984.042 ± 1890083.941  ops/s

我们看到递归解决方案仍然具有更高的吞吐量,但是,比 numberInt 时的 2.5 倍更小。

【讨论】:

  • 如果numberString 而不是 Int,那么可能值得测试一下性能。
  • @LuisMiguelMejíaSuárez 你的意思是这样吗scastie.scala-lang.org/FZu78b9BQSCZlgqXj0FS4Q
  • 是的,完全一样 - 如果它已经是 Int,我确定我的实现会慢一些,但不确定它是否已经是 String.
  • @LuisMiguelMejíaSuárez 递归仍然领先,但是,2.5 倍。
  • 哇,太棒了。在这种情况下,我想人们甚至可以通过逐个字符迭代 String 字符来使其更快。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-12-31
  • 2015-11-18
  • 1970-01-01
  • 1970-01-01
  • 2021-03-09
  • 1970-01-01
相关资源
最近更新 更多