첨가제 지속성


20

모든 가능성을 전달하는 가장 짧은 코드가 이깁니다.

수학에서 숫자지속성은 특정 고정 조건에 도달 할 때까지 숫자에 특정 연산을 적용해야하는 횟수를 측정합니다. 정수의 자릿수를 더하고 반복하여 양의 정수에 대한 추가 지속성을 확인할 수 있습니다. 한 자리 숫자를 찾을 때까지 합계 자리를 계속 추가합니다. 한 자릿수에 도달하는 데 걸리는 반복 횟수는 해당 숫자의 추가 지속성입니다.

84523을 사용하는 예 :

84523
8 + 4 + 5 + 2 + 3 = 22
2 + 2 = 4

It took two repetitions to find the single digit number.
So the additive persistence of 84523 is 2.

당신은 받게됩니다 순서 당신의 첨가제 지속성을 계산하기 위해이 양의 정수입니다. 각 줄은 처리 할 다른 정수를 포함합니다. 입력은 표준 I / O 방법으로 가능 합니다.

각 정수에 대해 정수, 그 뒤에 단일 공백, 그 뒤에 추가 지속성을 출력해야합니다. 처리 된 각 정수는 자체 행에 있어야합니다.

테스트 사례


입출력

99999999999 3
10 1
8 0
19999999999999999999999 4
6234 2
74621 2
39 2
2677889 3
0 0

1
테스트 사례에는 2 ^ 64가 넘는 일부 값이 포함되며 스펙에 따르면 프로그램은 최대 2 ^ 32의 값만 처리하면된다고합니다. 그것을 정리할 가치가 있습니다.
Peter Taylor

@ 피터 테일러, 그 한계를 제거하는 것을 잊었다. 프로그램이 내가 제공 한 입력을 처리 할 수 ​​있다면 제한에 문제가 없어야합니다.
Kevin Brown

5
999999999999의 지속성이 2가 아닌 3입니까?
Eelvex

@Evelex, 그것은 내가 생각하는 잘못된 마지막 순간의 변화였습니다. 결정된.
케빈 브라운

여기서 몇 가지 답변은 stdout에서 출력을 수행하는 것이 아니라 J의 "대화식"출력을 사용하여 명령 행 입력 후 결과를 반환하는 것입니다. (여기에는 2 개의 다른 J 답변이 포함되며 K 답변이라고 생각합니다.) 이것이 합법적 인 것으로 간주됩니까? 나는 18-ish 문자를 흘릴 수 있기 때문에.
Jesse Millikan

답변:


6

K-29 자

입력은 파일 이름을 포함하지 않는 29 개의 문자로 인수로 전달 된 파일 이름입니다.

`0:{5:x,-1+#(+/10_vs)\x}'.:'0:"file"
  • 35-> 31 : 외부 기능을 제거합니다.
  • 31-> 29 : 파 렌스 제거.

1
-1+#=>#1_
스트리트 스터

4

파이썬 84 문자

while 1:
 m=n=int(raw_input());c=0
 while n>9:c+=1;n=sum(map(int,str(n)))
 print m,c

도전 사례 : 06234.. 결과 성공적인 도전 :-)
Quixotic

@Debanjan 감사합니다. 수정했습니다.
fR0DDY


4

파이썬 (93 바이트)

f=lambda n,c:n>9and f(sum(map(int,str(n))),c+1)or c
while 1:n=int(raw_input());print n,f(n,0)

나는 당신이 사이의 공백을 제거 할 수 있다고 생각합니다 9...and
st0le

@ st0le : 감사합니다 :-)
Quixotic

그리고 input()대신 int(raw_input())....
st0le

@ st0le : 다음 입력을 수정하십시오 : 06234.
Quixotic

4

껍질 , 10 15 바이트

끔찍한 I / O 요구 사항에 +5 바이트

m(wΓ·,LU¡oΣdr)¶

온라인으로 사용해보십시오!

설명

여러 입력을 지원하려면 다음을 사용해야합니다 m(₁r)¶( 관심있는 계산을 수행하는 함수는 어디에 있습니까 ).

m(₁r)¶  -- expects newline-separated inputs: "x₁␤x₂␤…␤xₙ"
     ¶  -- split on newlines: ["x₁","x₂",…,"xₙ"]
m(  )   -- map over each string
 ( r)   -- | read integer: [x₁,x₂,…,xₙ]
 (₁ )   -- | apply the function described below

이 기능 은 다음을 수행합니다.

wΓ·,LU¡(Σd)  -- input is an integer, eg: 1234
      ¡(  )  -- iterate the following forever and collect results in list:
       ( d)  -- | digits: [1,2,3,4]
       (Σ )  -- | sum: 10
             -- : [1234,10,1,1,1,…
     U       -- keep longest prefix until repetition: [1234,10,1]
 Γ           -- pattern match (x = first element (1234), xs = tail ([10,1])) with:
  · L        -- | length of xs: 2
   ,         -- | construct tuple: (1234,2)
w            -- join with space: "1234 2"

3

배쉬, 105 자

while read x
do
for((i=0,z=x;x>9;i++))do
for((y=0;x>0;y+=x%10,x/=10))do :
done
x=$y
done
echo $z $i
done

실제로 어떤 골프도 관여하지는 않지만 개선 방법을 알 수 없습니다.



3

루비, 85 자

puts $<.map{|n|v=n.chop!;c=0;[c+=1,n="#{n.sum-n.size*48}"] while n[1];[v,c]*' '}*"\n"

Alex에서 "sum-size * 48"아이디어를 빌려야했습니다. 루비에서는 놓치기에는 너무 깔끔하기 때문입니다.


3

골프 스크립트, 40 자

n%{.:${;${48-}%{+}*`:$,}%.,1>\1?+' '\n}%

3

J-45 자

stdin에서 읽습니다.

(,' ',[:":@<:@#+/&.:("."0)^:a:)&><;._2(1!:1)3

나는 ^:a:나 자신 을 사용하려고 했지만 적절한 문서를 찾을 수 없었습니다 ... 어떤 힌트?
Eelvex

1
u ^ : n사전 항목 에는 사용법에 대한 정보가 있지만 약간 조밀합니다. ^ : a :는 다른 전원에 대한 호출과 같지만 결과를 수집하고 연속 호출에 대한 인수가 같을 때 종료됩니다 (수렴).
isawdrones

1
@Eelvex FWIW J 참조 카드a:^:a:트릭을 통해 발견 한 [PDF]
JB

@ JB : 그것은 ^:a:내가 아는 유일한 참고 자료입니다 : D
Eelvex

@ 엘 벡스. 나는 그 반대의 경험을했다. 사전에서 기능을 ^:(<'')발견하고 카드에서 발견 할 때까지 처음에 (아마 Kaprekar의 경우) 변형으로 사용 a:하여 행사 에 대해 배웠습니다 .
JB

3

c-519

(또는 프레임 워크에 대해 크레딧을 제공하는 경우 137)

이 작업 하나만 해결하는 대신 모든 지속성 문제 를 해결하기위한 프레임 워크를 만들기로 결정했습니다 .

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
typedef char*(*O)(char*);
char*b(char*s){long long int v=0,i,l=0;char*t=0;l=strlen(s);t=malloc(l+2);
for(i=0;i<l;i++)v+=s[i]-'0';snprintf(t,l+2,"%lld",v);return t;}
int a(char**s,O o){int r;char*n;n=o(*s);r=!strcmp(*s,n);free(*s);
*s=n;return r;}
int main(int c, char**v){size_t l, m=0;char *d,*n=0;O o=b;FILE*f=stdin;
while(((l=getline(&n,&m,f))>1)&&!feof(f)){int i=0;n=strsep(&n,"\n");
d=strdup(n);while(!a(&n,o))i++;printf("%s %d\n",d,i);free(d);free(n);n=0;m=0;}}

처음부터 시작하는 두 줄만 char*b이 문제에 고유합니다.

입력을 문자열로 취급합니다. 즉, 선행 "0"은 출력 단계 전에 스트립되지 않습니다.

위의 내용에는 주석, 오류 검사 및보고, 파일 읽기 (표준 입력에서 입력해야 함)가 다음과 같이 표시되어 있습니다.

/* persistence.c
 *
 * A general framework for finding the "persistence" of input strings
 * on opperations.
 *
 * Persistence is defined as the number of times we must apply
 *
 *    value_n+1 <-- Opperation(value_n)
 *
 * before we first reach a fixed point.
 */
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "../getline.h"

/* A function pointer type for operations */
typedef char*(op_func)(char*);
typedef op_func* op_ptr;
/* Op functions must
 * + Accept the signature above
 * + return a point to a newly allocated buffer containing the updated str
 */

char* addop(char*s){
  int i,l=0;
  long long int v=0;
  char *t=NULL;
  /* protect against bad input */
  if (NULL==s) return s;
  /* allocate the new buffer */
  l = strlen(s);
  t = malloc(l+2);
  if (NULL==t) return t;
  /* walk the characters of the original adding as we go */
  for (i=0; i<l; i++) v += s[i]-'0';
  //fprintf(stderr,"   '%s' (%d) yields %lld\n",s,l,v);
  snprintf(t,l+2,"%lld",v);
  //fprintf(stderr,"   %lld is converted to '%s'\n",v,t);
  return t;
}

/* Apply op(str), return true if the argument is a fixed point fo
 * falsse otherwise,
 */ 
int apply(char**str, op_ptr op){ 
  int r;
  char*nstr;
  /* protect against bad input */
  if ( NULL==op ) exit(1); 
  if ( NULL==*str ) exit(4); 
  /* apply */
  nstr = op(*str); 
  /* test for bad output */
  if ( NULL==nstr ) exit(2); 
  r = !strcmp(*str,nstr); 
  /* free previous buffer, and reasign the new one */
  free(*str); 
  *str = nstr; 
  return r; 
}

int main(int argc, char**argv){
  size_t len, llen=0;
  char *c,*line=NULL;
  op_ptr op=addop;
  FILE *f=stdin;
  if (argc > 1) f = fopen(argv[1],"r");
  while( ((len=getline(&line,&llen,f))>1) && line!=NULL && !feof(f) ){
    int i=0;
    line=strsep(&line,"\n"); // Strip the ending newline
    /* keep a copy for later */
    c = strdup(line);
    /* count necessary applications */
    while(!apply(&line,op)) i++;
    printf("%s %d\n",c,i);
    /* memory management */
    free(c);
    free(line);
    line=NULL;
    llen=0;
  }
}

우리가 체처럼 메모리를 누출하려고한다면 조금 더 절약 할 수 있습니다. 마찬가지로 #definereturn 등을 사용 하여이 시점에서 나는 그것을 더 추악하게 만들지 않아도됩니다.



2

J, 74 자

i=:<;._2(1!:1)3
i&((],' ',":@(0 i.~9<[:".([:":[:+/"."0)^:(i.9)))@>@{~)i.#i

편집

  • (86 → 83) 일부 캡 [:ATS에@
  • (83 → 79) 불필요한 괄호
  • (→ 75 79) 변경 0".".단순화 것들
  • (75 → 74) 더 나은 절단

예 :

i=:<;._2(1!:1)3
74621
39
2677889
0
i&((],' ',":@(0 i.~9<[:".([:":[:+/"."0)^:(i.9)))@>@{~)i.#i
74621 2  
39 2     
2677889 3
0 0  

여러 입력에 대해 출력 형식이 잘못되었습니다. "단일 공간"참조
Jesse Millikan

@Jesse : 아무 것도 잘못 보지 않습니다. 예를 들어 주시겠습니까?
Eelvex

나는 전혀 모른다, 나는 내가 추측하는 것을보고있다.
Jesse Millikan

1

나는 이것이 내가 생각해 낼 수있는 최선의 것이라고 생각한다.

루비 101 문자

f=->(n){n.sum-n.size*48}
$<.each{|l|i=0;i+=1 while(i+=1;n=f[(n||l.chop!).to_s])>10
puts "#{l} #{i}"}

실은 잘게! 씹는 대신에! 하나의 문자 절약을 제공합니다. 97 자
Alex Bartlow

91 개 문자로 골프를 더 했어요.
Alex Bartlow

1

PARI / GP 101 문자

s(n)=r=0;while(n>0,r+=n%10;n\=10);r
f(n)=c=0;while(n>9,c++;n=s(n));c
while(n=input(),print(n," ",f(n)))

불행히도 GP에는 입력 기능이 없으므로 IO 부분이 부족하다고 생각합니다. :( 고정 : Eelvex 감사합니다! :)


물론이 : input():)
Eelvex

@ 엘 벡스. :)
st0le

1

자바 스크립트-95

i=prompt();while(i>9){i=''+i;t=0;for(j=0;j<i.length;j++)t+=parseInt(i.charAt(j));i=t;}alert(t);

편집 : ops은 여러 줄을하지 않습니다


1
이것이 올바르게 출력되지 않는 것을 알았습니다.
Kevin Brown

1

J, 78

f=:[:+/"."0&":
r=:>:@$:@f`0:@.(=f)
(4(1!:2)~LF,~[:":@([,r)".@,&'x');._2(1!:1)3

재귀 솔루션. stdin에서 읽습니다. stdout 으로 작성하므로 여유를 줄이십시오-여분의 18 문자가 필요합니다.


1

펄-77 자

sub'_{split//,shift;@_<2?0:1+_(eval join'+',@_)}chop,print$_,$",(_$_),$/for<>

1

자바 스크립트 , 57 47 bytes

-10 bytes thanks to @l4m2!

f=(s,c=0)=>s>9?f(eval([...s+""].join`+`),++c):c

Try it online!


f=(s,c=0)=>s>9?f([...s+""].reduce((x,y)=>x*1+y*1),++c):c
l4m2

f=(s,c=0)=>s>9?f([...s+""].reduce((x,y)=>x- -y),++c):c
l4m2

1
f=(s,c=0)=>s>9?f(eval([...s+""].join`+`)),++c):c
l4m2

@l4m2 Thanks! s>9 and eval were great ideas. I think you had an extra paren in there, making it a total of 10 bytes you saved me :-)
Oliver

Note the strict I/O ;)
Shaggy

1

05AB1E, 13 bytes

ε.µΔSO¼}¾}<ø»

Input as a list of integers.

Try it online.

Explanation:

ε     # Map each integer in the (implicit) input to:
    #  Reset the counter variable to 0
 Δ    #  Loop until the integer no longer changes:
  S   #   Convert it to a list of digits
   O  #   And take the sum of those
  ¼   #   Increase the counter variable by 1
    #  After the inner loop: Push the counter variable
}<    # After the map: decrease each value by 1
  ø   # Zip/transpose it with the (implicit) input to create a paired list
   »  # Join each pair by a space, and then each string by newlines
      # (after which the result is output implicitly)

1

MathGolf, 11 bytes

hÅ_Σ]▀£(k ?

Try it online!

Incredibly inefficient, but we don't care about that. Basically, using the fact that the additive persistence of a number is smaller than or equal to the number itself.

Uses the fact that the additive persistence is less than or equal to the number of digits of the number. Passes all test cases with ease now.

The input format, while suboptimal for some languages, is actually the standard method of taking multiple test cases as input in MathGolf. Each line of the input is processed as its own program execution, and output is separated by a single newline for each execution.

Explanation (using n = 6234)

h             push length of number without popping (6234, 4)
 Å            loop 4 times using next 2 operators
  _           duplicate TOS
   Σ          get the digit sum
    ]         wrap stack in array
              this gives the array [6234, 15, 6, 6, 6]
     ▀        unique elements of string/list ([6234, 15, 6])
      £       length of array/string with pop (3)
       (      decrement (2)
        k ?   push input, space, and rotate top 3 elements to produce output (6234 2)

1

K (ngn/k), 16 bytes

Solution:

{x,#1_(+/10\)\x} 

Try it online!

Explanation:

{x,#1_(+/10\)\x} / the solution
{              } / lambda taking implicit x
      (     )\x  / iterate until convergence
         10\     / split into base-10 (123 => 1 2 3)
       +/        / sum
    1_           / drop first result (iterate returns input as first result)
   #             / count length of result
 x,              / prepend x (original input)


0

scala 173:

def s(n:BigInt):BigInt=if(n<=9)n else n%10+s(n/10)
def d(n:BigInt):Int=if(n<10)0 else 1+d(s(n))
Iterator.continually(readInt).takeWhile(_>0).foreach(i=>println(i+" "+d(i)))



0

Python 3, 82 bytes

while 1:f=lambda n:n//10and 1+f(sum(map(int,str(n))));i=input();print(i,f(int(i)))

0

Tcl, 95 bytes

proc P {v n\ 0} {set V $v
while \$v>9 {set v [expr [join [split $v ""] +]]
incr n}
puts $V\ $n}

Try it online!


3
Because the next newest answer is a full 6 years old, which i think is before TIO existed
fəˈnɛtɪk

0

Japt, 28 bytes

Ë+S+(@D=X©A<D©ì x ªD D<AÃa÷
Ë                            // Map over the inputs and return each, followed by
 +S+                         // a space, followed by the number's persistence.
      D=     ©ì x            // To find it, fold the number up
        X©A<D     ªD         // if we can (handles unfoldable cases),
    (@               D<AÃa   // until it can't be folded up any further.
                          ÷ // Then, join everything up with newlines.

Try it online!


0

PHP, 72+1 bytes

+1 for -R flag.

for($i=0,$a=$argn;$a>9;$i++)$a=array_sum(str_split($a));echo"$argn $i
";

Run as pipe with -R.

  • running PHP as pipe will execute the code once for every input line
  • but it does not unset variables inbetween; so $i must be initialized.
    (Also, it would print nothing instead of 0 for single digits without the initialization.)

0

Bash+coreutils, 83 bytes

[ $1 -le 9 ]&&exit $2
let x=$2+1
for z in `fold -w1<<<$1`
do let y+=$z
done
a $y $x

Try it online!

Should be saved to a script called a and placed in the system's PATH, as it calls itself recursively. Takes input from command line, like a 1999. Returns by exit code.

TIO has some limitations on what you can do with a script, so there's some boilerplate code to make this run in the header.

Prints an error to stderr for input larger than bash integers can handle, but since the actual computation is done with strings, it still gives the right result anyway.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.