用最大位数减少数字


33

任务:

给定十进制数字系统中的整数,将其减少为一个十进制数字,如下所示:

  1. 将数字转换为十进制数字列表。
  2. 找出最大的数字D
  3. 从列表中删除D。如果出现多个D,请从左侧选择第一个(最重要的位置),所有其他D应保持不变。
  4. 将结果列表转换为十进制数字,然后将其乘以D。
  5. 如果数字大于9(具有超过1个十进制数字),请重复整个过程,并将结果输入其中。得到一个数字的结果时停止。
  6. 显示结果。

例:

26364 -> 
1. 2 6 3 6 4 
2. The largest digit is 6, so D=6
3. There are two occurrences or 6: at positions 1 and 3 (0-based). We remove the left one,
    at position 1 and get the list 2 3 6 4 
4. we convert the list 2 3 6 4 to 2364 and multiply it by D:
   2364 * 6 = 14184
5. 14184 is greater than 9 so we repeat the procedure, feeding 14184 into it.

我们继续对14184重复该过程,依此类推,然后通过以下中间结果,最终达到8:

11312
3336
1998
1782
1376
952
468
368
288
224
88
64
24
8

所以26364的结果是8。

输入:整数/代表整数的字符串

输出:一位数,减法的结果应用于数字。

测试用例:

9 -> 9
27 -> 4
757 -> 5
1234 -> 8
26364 -> 8
432969 -> 0
1234584 -> 8
91273716 -> 6

这是,因此每种语言中以字节为单位的最短答案都将获胜。


3
如果数字大于10具有大于1的十进制数字,那是哪个。数字10的十进制数字大于1,但不大于10。
亚当

@Adám通过编码逻辑,然后10 -> 10
伊恩H.17年

1
@Adám是的,我应该写成“大于9”。我将编辑描述。谢谢!
Galen Ivanov

有人检查过此功能的直方图是否足够大的区域吗?似乎有很多零。在编写测试用例时,我也得到了很多8分。
Galen Ivanov

2
此外,被4整除的随机数具有3/5的可能性,即最后两位数字的乘积可被8整除。
ØrjanJohansen

Answers:


18

05AB1E,6个字节

码:

[Dg#à*

使用05AB1E编码。在线尝试!

说明

[Dg#     # While the length of the number is not 1
    à    # Extract the largest element from the current number
     *   # Multiply it with the leftover number

11

JavaScript(ES6),49个字节

f=n=>n>9?f(""+n.replace(m=Math.max(...n),"")*m):n

将输入作为整数的字符串表示形式,例如f("26364")

测试用例



6

Pyth,16个字节

.WtH`*s.-ZKeSZsK

将输入作为字符串。在这里尝试! (备选:.WtH`*s.-ZeSZseS

Pyth,18个字节

.WgHT*s.-`ZKeS`ZsK

将输入作为整数。在这里尝试!

怎么运行的

16人

.WtH` * s.-ZKeSZsK〜完整程序。

.W〜功能片刻。虽然A(值)是真实的,但值= B(值)。
                 〜返回最终值。
  tH〜A,条件:值[1:]是否正确?长度是否≥2?
    `* s。-ZKeSZsK〜B,二传手。
       .-〜Bagwise减法,用于删除最高位数,用...
         Z〜当前值Z,...
          KeSZ〜Z的最高数字(作为字符串)。还分配给变量K。
      s〜强制转换为整数。
     *〜乘以...
              sK〜最高位数。
    `〜转换为字符串。

18人

.WgHT * s。-`ZKeS`ZsK〜完整程序。

.W〜功能片刻。虽然A(值)是真实的,但值= B(值)。
                   〜返回最终值。
  gHT〜A,条件:值(H)≥10吗?
     * s.-`ZKeS`ZsK〜B,二传手。
       .-〜Bagwise减法(用于删除第一次出现的值)。
         Z〜Z的字符串表示形式。
           KeS`Z〜和Z的最高(按字法)字符(最高数字)。
                     它还将其分配给名为K的变量。
      s〜转换为整数。
     *〜乘以...
                sK〜K转换为int。

存在 有近果冻在这样类型的挑战是为Pyth很好IMO :-)


6

稻壳14岁 13 12字节

感谢Zgarb保存1个字节。

Ω≤9oṠS*od-▲d

在线尝试!

说明:

Ω≤9            Repeat the following function until the result is ≤ 9
           d     Convert to a list of digits
         -▲      Remove the largest one
       od        Convert back to an integer
   oṠS*          Multiply by the maximum digit

12个字节,并进行了一些重新排列。
Zgarb

@Zgarb谢谢,我一直在寻找类似的东西。
H.PWiz

6

R99 95字节

f=function(x)"if"(n<-nchar(x)-1,f(10^(n:1-1)%*%(d=x%/%10^(n:0)%%10)[-(M=which.max(d))]*d[M]),x)

在线尝试!

递归函数。添加f(number)页脚可用于测试的其他值number。简单明了的实现d是数字列表,并10^(n:2-2)%*%d[-M]计算去除了最大数字的数字。


5

Python 2,72个字节

f=lambda n:`n`*(n<=9)or f(int(`n`.replace(max(`n`),'',1))*int(max(`n`)))

在线尝试!


1
......我在调试一个愚蠢的错误。该死,我忍者了。
totallyhuman

输入9时出现错误
RoryT

对于测试用例,这似乎失败了432969。“ ValueError:int()以10为底的无效文字:“”
James Webster

@JamesWebster现在应该修复。
FlipTack

1
@recursive否,因为如果n当时为0,则n*(n<=9)仍将求值为假值0,从而使递归继续进行并导致错误,而字符串'0'是真实值,因此暂停递归。
FlipTack


4

果冻,15 字节

D×Ṁ$œṡṀ$FḌµ>9µ¿

在线尝试!或见测试人员

怎么样?

D×Ṁ$œṡṀ$FḌµ>9µ¿ - Link: number, n
              ¿ - while:
             µ  - ...condition (monadic):
            9   -    literal 9
           >    -    loop value greater than (9)?
          µ     - ...do (monadic):               e.g. 432969
D               -    convert to a decimal list        [4,3,2,9,6,9]
   $            -    last two links as a monad:
  Ṁ             -      maximum                         9
 ×              -      multiply (vectorises)          [36,27,18,81,54,81]
       $        -    last two links as a monad:
      Ṁ         -      maximum                         81
    œṡ          -      split at first occurrence      [[36,27,18],[54,81]]
        F       -    flatten                          [36,27,18,54,81]
         Ḍ      -    convert from base 10              389421  (i.e. 360000 + 27000 + 1800 + 540 + 81)


4

C#(.NET Core),126字节

int F(int n){var x=(n+"").ToList();var m=x.Max();x.RemoveAt(x.IndexOf(m));return n>9?F(int.Parse(string.Concat(x))*(m-48)):n;}

在线尝试!



@EriktheOutgolfer谢谢,错过了那个。
Timmeh

1
@totallyhuman谢谢,经过一些重构后降至137。
Timmeh,

您可以if(n<10)return n;...return F(...);使用三进制-if 更改为单返回,例如:int F(int n){var x=(n+"").ToList();var m=x.Max(d=>d);x.RemoveAt(x.IndexOf(m));return n<10?n:F(int.Parse(string.Concat(x))*(m-48));}131 bytes
-if

我认为您需要在using System.Linq;字节数中包含(18个字节)。
伊恩H.17年

4

APL(Dyalog)36 35 33字节

-1由于更新了OP规范。-2感谢ngn。

匿名默认前缀功能。以整数作为参数。

{⍵>9:∇(⌈/×10⊥⊂⌷⍨¨⍳∘≢~⊢⍳⌈/)⍎¨⍕⍵⋄⍵}

在线尝试!

{}一个参数在哪里的函数:

⍵>9: 如果参数大于9,则:

  ⍕⍵ 格式化(字符串化)参数

  ⍎¨ 分别执行(评估)(这使我们获得了数字作为数字)

  () 对那些应用以下默认功能

   ⌈/ 最大位数

   × 次

   10⊥ (收集数字)的以10为底的解码

    所有数字

   ⌷⍨¨ 由每个索引

   ⍳∘≢ 在的位数的ndices

    不同于

   ⊢⍳⌈/ 最大的数字是i ndex在数字的整个列表

   递归(即自我称呼)

 其他

   返回未修改的参数



@EriktheOutgolfer可能,但是OP实际上对此并不清楚(自相矛盾)。
亚当

没错,但是>9可以节省一个字节。
暴民埃里克(Erik the Outgolfer)'17年

@EriktheOutgolfer更新。
亚当

@亚当∇代替⍣=用于-1字节:{⍵> 9:∇(⌈/ ...⋄⍵}
NGN

3

Perl 6的 45  41个字节

{($_,{$/=.comb.max;S/"$/"//*$/}...10>*).tail}

测试一下

{($_,{S/"{.comb.max}"//*$/}...10>*).tail}

测试一下

展开:

{  # bare block lambda with implicit parameter 「$_」

  (  # generate the sequence

      $_,                      # start the sequence with the input

      {                        # generate the rest of the values in the sequence

          S/                   # find and replace (not in-place)
            "{  .comb.max  }"  # find the max digit and match against it
          //                   # replace it with nothing
          *                    # multiply the result with
          $/                   # the digit that was removed
      }

      ...                      # keep generating values until

      10 > *                   # the value is less than 10

  ).tail                       # get the last value from the sequence
}

3

视网膜,67字节

{1`(..+)?
1$&;$&
O`\G\d
.+((.);.*?)\2
$1
\d+
$*
1(?=.*;(1+))|.
$1
1

在线尝试!Link包括足够快的测试用例,不会影响Dennis的服务器。说明:

{1`(..+)?
1$&;$&

对于两位数的数字,这将使用;分隔符来复制该数字,并在重复项前添加1。对于一位数字,这是数字的前缀1;

O`\G\d

排序重复项的数字。(对于一位数字,这无效。)

.+((.);.*?)\2
$1

找到第一个出现的最大数字,并将其删除,再删除重复的其他数字,以及先前添加的额外的1。(对于一位数字,匹配失败,因此无济于事。)

\d+
$*
1(?=.*;(1+))|.
$1
1

将数字乘以数字。对于一位数字,这将得到原始数字,然后循环终止。否则,程序将循环直到达到一位数字。


3

C#(.NET Core)177164 + 18字节

感谢@raznagul,节省了13个字节!

int f(int n){string s=n+"",m=s.Max(d=>d)+"";if(n<10)return n;var x=s.ToList();x.RemoveAt(s.IndexOf(m));int y=int.Parse(string.Join("",x))*int.Parse(m);return f(y);}

在线尝试!


您可以更改s.Length<2n<10。另外,您可以删除三元运算符,并且只需return f(y)在结尾处删除即可,因为if递归的下一步中的情况是这样处理的。
raznagul

3

Java 8,126 104字节

n->{for(;n>9;n=new Long((n+"").replaceFirst((n=(n+"").chars().max().getAsInt()-48)+"",""))*n);return n;}

-22字节的感谢@OlivierGrégoire

说明:

在这里尝试。

n->{         // Method with long as both parameter and return-type
  for(;n>9;  //  Loop as long as the number contains more than 1 digit
    n=       //   Replace the current number with:
      new Long((n+"").replaceFirst((n=(n+"").chars().max().getAsInt()-48)+"",""))
             //    Remove the first largest digit from the number,
      *n     //    and multiply this new number with the removed digit
  );         //  End of loop
  return n;  //  Return the result
}            // End of method


1
104个字节(与上述相同,但也是迭代而不是递归的,而且:n>9并且还原了条件而不是n<10)。
OlivierGrégoire17年

2

jQuery 1.5,86个字节

until(.<10;"\(.)"|(./""|max)as$v|index($v)as$x|.[:$x]+.[1+$x:]|tonumber*($v|tonumber))

展开式

until(
    .<10                    # until number is below 10
  ; "\(.)"                  # convert to string
  | (./""|max) as $v        # find largest digit, call it $v
  | index($v) as $x         # find index of digit
  | .[:$x]+.[1+$x:]         # remove digit
  | tonumber*($v|tonumber)  # convert back to number and multiply by $v
)

在线尝试!



2

Lua中,137 108个字节

function f(n)while n>9 do b="0"g=b.gsub g(n,".",function(m)b=math.max(m,b)end)n=b*g(n,b,"",1)end print(n)end

感谢Jonathan S赢得了29个字节。

在线尝试!



谢谢。看起来值得自己回答-将链接到您为此撰写的帖子,否则将进行编辑和评分。
MCAdventure17年

只需对其进行编辑。它仍然是您的代码,我还没有从头开始编写它。
Jonathan S.

2

d188个 186 185字节

import std.conv,std.algorithm;T f(T,U=string)(T u){if(u<10)return u;T[]r;u.text.each!(n=>r~=n.to!T-48);T m=r.maxElement;U s;r.remove(r.maxIndex).each!(n=>s~=n.to!U);return f(m*s.to!T);}

在线尝试!

我非常讨厌懒惰的评价。欢迎任何提示!


2

Lua,154字节

我现在应该尝试一些方法来解决这个问题。

n=...z=table
while n+0>9 do
t={}T={}n=n..''n:gsub(".",function(c)t[#t+1]=c T[#T+1]=c
end)z.sort(t)x=t[#t]z.remove(T,n:find(x))n=z.concat(T)*x
end
print(n)

在线尝试!

说明

n=...                    -- define n as a shorthand for the argument
z=table                  -- define z as a pointer to the object table
while n+0>9              -- iterate as long as n is greater than 9
do                       -- n+0 ensure that we're using a number to do the comparison
  t={}                   -- intialise two tables, one is used to find the greatest digit
  T={}                   -- the other one is used to remove it from the string
  n=n..''                -- ensure that n is a string (mandatory after the first loop)
  n:gsub(".",function(c) -- apply an anonymous function to each character in n
               t[#t+1]=c -- fill our tables with the digits
               T[#T+1]=c
             end)        
  z.sort(t)              -- sort t to put the greatest digit in the last index
  x=t[#t]                -- intialise x to the value of the greatest digit
  z.remove(T,n:find(x))  -- remove the first occurence of x from the table T 
                         -- based on its position in the input string
  n=z.concat(T)*x        -- assign the new value to n
end                      -- if it still isn't a single digit, we're looping over again
print(n)                 -- output the answer

2

PowerShell,123字节

[Collections.ArrayList]$a=[char[]]"$args"
while(9-lt-join$a){$a.remove(($b=($a|sort)[-1]));$a=[char[]]"$(+"$b"*-join$a)"}$a

在线尝试!

哎呀 PowerShell数组是不可变的,因此我们需要在[Collections.ArrayList]此处使用冗长的转换,以便我们可以调用.remove()稍后。

接受输入$args,将其转换成字符串,然后是char-array,然后是a ArrayList。将其存储到中$a。然后while循环播放,直到达到或低于此值9。每次迭代,我们调用.remove的最大元素$a(通过完成sort和采取的最后一个元素[-1]),最大元素存储到$b在同一时间。发生这种情况是因为ASCII值与文字数字的排序方式相同。

接下来,我们重新计算$a,重新作为一个char阵列(和ArrayList隐式),铸造我们的$b(这是目前一char)为一个字符串,然后用一个int +,并乘,要$a -join ed转换为字符串(隐式转换为int)。这满足了挑战的“乘以D”部分。

最后,一旦脱离循环,我们便$a进入了管道,并且输出是隐式的。


2

22 21字节

Wa>9a:aRAa@?YMXax*:ya

将输入作为命令行参数。验证所有测试用例:在线尝试!

说明

取消评论,并附有评论:

                 a is 1st cmdline arg
W a>9 {          While a > 9:
  Y MXa           Yank max(a) into y
  a RA: a@?y ""   Find index of y in a; replace the character at that position with ""
  a *: y          Multiply a by y
}
a                Autoprint a

在高尔夫球版本中,循环主体被压缩为一个表达式:

a:aRAa@?YMXax*:y
        YMXa      Yank max(a)
     a@?          Find its index in a
  aRA       x     Replace at that index with x (preinitialized to "")
             *:y  Multiply that result by y (using : meta-operator to lower the precedence)
a:                Assign back to a


2

Java 8:115个字节


感谢Jo King提供的-10个字节

不幸的是,您无法递归调用lambda函数,因此方法标头需要额外的11个字节。我知道有一个较短的Java答案循环出现,但是我决定自己解决这个问题。

long f(long n){int m=(n+"").chars().max().getAsInt()-48;return n>9?f(new Long((n+"").replaceFirst(""+m,""))*m):n;};

在线尝试


您可以将其-48从地图移至m定义的末尾。在线尝试!您的TIO链接中还包含一些额外的空格
乔·金

@JoKing谢谢。
本杰明·厄克特

1

J,40个字节

((]*<^:3@i.{[)>./)&.(10&#.inv)^:(9&<)^:_

在线尝试!

说明

(      iterate                   )^:(9&<)^:_    NB. keep iterating while the number is > 9
 (     stuff         )&.(10&#.inv)              NB. convert to digits, do stuff, convert back to number
 (           )>./)                              NB. stuff is a hook, with max digit >./  on the right
 (]*<^:3@i.{[)                                  NB. so that in this phrase, ] means "max" and [ means "all digits"
  ]                                             NB. the max digit...
   *                                            NB. times...        
    <^:3@                                       NB. triple box...
         i.                                     NB. the first index of the max in the list of all digits
           {                                    NB. "from" -- which because of the triple box means "take all indexes except..."
            [                                   NB. from all the digits of the number

1
我今天从您那里了解了有关三重盒子选择的信息,谢谢!
Galen Ivanov

1

PowerShell,230字节

$n="$args";do{$n=$n.ToString();$a=@();0..$n.Length|%{$a+=$n[$_]};$g=[convert]::ToInt32(($a|sort|select -last 1),10);[regex]$p=$g.ToString();[int]$s=$p.replace($n,'',1);if($n.Length-eq1){$n;exit}else{$r=$s*$g}$n=$r}until($r-lt10)$r

在线尝试!

在所有类型的铸件上浪费太多。


1

PHP,82 77 + 1字节

for($n=$argn;$n>9;)$n=join("",explode($d=max(str_split($n)),$n,2))*$d;echo$n;

与管道一起运行-nR在线尝试


1

直流98 85字节

?dsj[0dsosclj[soIlc^sr0]sn[I~dlo!>nrlc1+scd0<i]dsixljdlr%rlrI*/lr*+lo*dsj9<T]sT9<Tljp

非常感谢此答案所带来的想法,即利用~从数字中提取数字,从而在代码的原始版本上节省了两个字节。

这是一个相当完善的功能dc,它不存在字符串处理功能。

在线尝试!


1

Bash,80个字节

使用软件包Core Utilities(用于sorttail)和grep

while((n>9));do m=$(grep -o .<<<$n|sort|tail -n1);n=$((${n/$m/}*m));done;echo $n

它是如何工作的?

while (( n > 9 )); do  # C-style loop conditional
    grep -o .          # Separate the string into one char per line
              <<< $n   # Use the content of variable `n` as its stdin
    | sort             # Pipe to `sort`, which sorts strings by line
    | tail -n 1        # Take the last line

m=$(                 ) # Assign the output of the command chain to `m`
n=$((          ))      # Assign the result of the evaluation to n
     ${n/$m/}          # Replace the first occurrence of $m with empty
             *m        # ... and multiply it by the value of `m`
done; echo $n          # After loop, print the value of `n`
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.