Happy numbers: Difference between revisions
m
→{{header|Uiua}}: slightly nicer algorithm
mNo edit summary |
m (→{{header|Uiua}}: slightly nicer algorithm) |
||
(27 intermediate revisions by 14 users not shown) | |||
Line 15:
Display an example of your output here on this page.
;Related tasks:
* [[Iterated digits squaring]]
;See also:
Line 180 ⟶ 183:
</pre>
=={{header|ABC}}==
<syntaxhighlight lang="ABC">HOW TO RETURN square.digit.sum n:
PUT 0 IN sum
WHILE n>0:
PUT n mod 10 IN digit
PUT sum + digit ** 2 IN sum
PUT floor (n/10) IN n
RETURN sum
HOW TO REPORT happy n:
PUT {} IN seen
WHILE n not.in seen:
INSERT n IN seen
PUT square.digit.sum n IN n
REPORT n=1
HOW TO RETURN next.happy n:
PUT n+1 IN n
WHILE NOT happy n: PUT n+1 IN n
RETURN n
PUT 0 IN n
FOR i IN {1..8}:
PUT next.happy n IN n
WRITE n/</syntaxhighlight>
{{out}}
<Pre>1
7
10
13
19
23
28
31</pre>
=={{header|ACL2}}==
<syntaxhighlight lang="lisp">(include-book "arithmetic-3/top" :dir :system)
Line 467 ⟶ 504:
=={{header|ALGOL W}}==
<syntaxhighlight lang="algolw">
% when repeatedly applied %
% returns true if n is happy, false otherwise %
logical procedure isHappy ( integer value n ) ;
begin
% in base ten, numbers either reach 1 or loop around a sequence %
% containing 4 (see the Wikipedia article) %
while begin
dSum := 0;
while v not = 0 do begin
d := v rem 10;
v := v div 10;
dSum := dSum + ( d * d )
end while_v_ne_0 ;
v := dSum;
v not = 1 and v not = 4
end do begin end
end if_v_ne_0 ;
v = 1
end isHappy ;
begin % find the first 8 happy numbers %
integer n, hCount;
hCount := 0;
n := 1;
while hCount < 8 do begin
if isHappy( n ) then begin
writeon( i_w := 1, s_w := 0, " ", n );
end
n := n + 1
end
end
end.
</syntaxhighlight>
{{out}}
<pre>
</pre>
Line 2,179 ⟶ 2,200:
28
31</pre>
=={{header|COBOL}}==
<syntaxhighlight lang="cobol"> IDENTIFICATION DIVISION.
PROGRAM-ID. HAPPY.
DATA DIVISION.
WORKING-STORAGE SECTION.
01 VARIABLES.
03 CANDIDATE PIC 9(4).
03 SQSUM-IN PIC 9(4).
03 FILLER REDEFINES SQSUM-IN.
05 DIGITS PIC 9 OCCURS 4 TIMES.
03 SQUARE PIC 9(4).
03 SUM-OF-SQUARES PIC 9(4).
03 N PIC 9.
03 TORTOISE PIC 9(4).
03 HARE PIC 9(4).
88 HAPPY VALUE 1.
03 SEEN PIC 9 VALUE ZERO.
03 OUT-FMT PIC ZZZ9.
PROCEDURE DIVISION.
BEGIN.
PERFORM DISPLAY-IF-HAPPY VARYING CANDIDATE FROM 1 BY 1
UNTIL SEEN IS EQUAL TO 8.
STOP RUN.
DISPLAY-IF-HAPPY.
PERFORM CHECK-HAPPY.
IF HAPPY,
MOVE CANDIDATE TO OUT-FMT,
DISPLAY OUT-FMT,
ADD 1 TO SEEN.
CHECK-HAPPY.
MOVE CANDIDATE TO TORTOISE, SQSUM-IN.
PERFORM CALC-SUM-OF-SQUARES.
MOVE SUM-OF-SQUARES TO HARE.
PERFORM CHECK-HAPPY-STEP UNTIL TORTOISE IS EQUAL TO HARE.
CHECK-HAPPY-STEP.
MOVE TORTOISE TO SQSUM-IN.
PERFORM CALC-SUM-OF-SQUARES.
MOVE SUM-OF-SQUARES TO TORTOISE.
MOVE HARE TO SQSUM-IN.
PERFORM CALC-SUM-OF-SQUARES.
MOVE SUM-OF-SQUARES TO SQSUM-IN.
PERFORM CALC-SUM-OF-SQUARES.
MOVE SUM-OF-SQUARES TO HARE.
CALC-SUM-OF-SQUARES.
MOVE ZERO TO SUM-OF-SQUARES.
PERFORM ADD-DIGIT-SQUARE VARYING N FROM 1 BY 1
UNTIL N IS GREATER THAN 4.
ADD-DIGIT-SQUARE.
MULTIPLY DIGITS(N) BY DIGITS(N) GIVING SQUARE.
ADD SQUARE TO SUM-OF-SQUARES.</syntaxhighlight>
{{out}}
<pre> 1
7
10
13
19
23
28
31</pre>
=={{header|CoffeeScript}}==
Line 2,755 ⟶ 2,843:
if ((count += 1) >= 8) { break }
}</syntaxhighlight>
=={{header|EasyLang}}==
<syntaxhighlight>
func dsum n .
while n > 0
d = n mod 10
s += d * d
n = n div 10
.
return s
.
func happy n .
while n > 999
n = dsum n
.
len seen[] 999
repeat
n = dsum n
until seen[n] = 1
seen[n] = 1
.
return if n = 1
.
while cnt < 8
n += 1
if happy n = 1
cnt += 1
write n & " "
.
.
</syntaxhighlight>
{{out}}
<pre>
1 7 10 13 19 23 28 31
</pre>
=={{header|Eiffel}}==
Line 2,833 ⟶ 2,956:
=={{header|Elena}}==
{{trans|C#}}
ELENA
<syntaxhighlight lang="elena">import extensions;
import system'collections;
Line 2,845 ⟶ 2,968:
while (num != 1)
{
if (cache.indexOfElement
{
^ false
Line 2,852 ⟶ 2,975:
while (num != 0)
{
int digit := num.mod
sum += (digit*digit);
num /= 10
Line 3,386 ⟶ 3,509:
=={{header|Fōrmulæ}}==
{{FormulaeEntry|page=https://formulae.org/?script=examples/Happy_numbers}}
'''Solution.'''
The following function returns whether a given number is happy or not:
[[File:Fōrmulæ - Happy numbers 01.png]]
Retrieving the first 8 happy numbers
[[File:Fōrmulæ - Happy numbers 02.png]]
[[File:Fōrmulæ - Happy numbers 03.png]]
=={{header|Go}}==
Line 3,875 ⟶ 4,006:
<syntaxhighlight lang="julia">
function happy(x)
happy_ints =
int_try = 1
while length(happy_ints) < x
n = int_try
past =
while n != 1
push!(past, n)
end
n == 1 && push!(happy_ints,int_try)
int_try += 1
Line 3,903 ⟶ 4,035:
<syntaxhighlight lang="julia">sumhappy(n) = sum(x->x^2, digits(n))
function ishappy(x, mem = Int[])
x == 1 ? true :
x in mem ? false :
ishappy(sumhappy(x), [mem ; x])
end
nexthappy
happy(n) = accumulate((a, b) -> nexthappy(a), 1:n)
</syntaxhighlight>
{{Out}}
Line 3,921 ⟶ 4,052:
{{trans|C}}
<syntaxhighlight lang="julia">const CACHE = 256
buf = zeros(Int, CACHE)
buf[
function happy(n)
if n < CACHE
Line 3,929 ⟶ 4,060:
buf[n] = 2
end
nn = n
while nn != 0
nn, x = divrem(nn
end
x = happy(
n < CACHE && (buf[n] = 2 - x)
return x
end
function main()
i, counter = 1
while counter > 0
if happy(i)
counter -= 1
end
i += 1
end
return i - 1
end
</syntaxhighlight>
=={{header|K}}==
Line 4,021 ⟶ 4,153:
First 8 happy numbers : 1, 7, 10, 13, 19, 23, 28, 31
</pre>
=={{header|Lambdatalk}}==
<syntaxhighlight lang="scheme">
{def happy
{def happy.sum
{lambda {:n}
{if {= {W.length :n} 1}
then {pow {W.first :n} 2}
else {+ {pow {W.first :n} 2}
{happy.sum {W.rest :n}}}}}}
{def happy.is
{lambda {:x :a}
{if {= :x 1}
then true
else {if {> {A.in? :x :a} -1}
then false
else {happy.is {happy.sum :x}
{A.addlast! :x :a}}}}}}
{def happy.rec
{lambda {:n :a :i}
{if {= {A.length :a} :n}
then :a
else {happy.rec :n
{if {happy.is :i {A.new}}
then {A.addlast! :i :a}
else :a}
{+ :i 1}}}}}
{lambda {:n}
{happy.rec :n {A.new} 0}}}
-> happy
{happy 8}
-> [1,7,10,13,19,23,28,31]
</syntaxhighlight>
=={{header|Lasso}}==
Line 4,237 ⟶ 4,403:
1
7
10
13
19
23
28
31</pre>
=={{header|MACRO-11}}==
<syntaxhighlight lang="macro11"> .TITLE HAPPY
.MCALL .TTYOUT,.EXIT
HAPPY:: MOV #^D8,R5 ; 8 HAPPY NUMBERS
CLR R4
1$: INC R4
MOV R4,R0
JSR PC,CHECK
BNE 1$
MOV R4,R0
JSR PC,PR0
SOB R5,1$
.EXIT
; CHECK IF R0 IS HAPPY: ZERO FLAG SET IF TRUE
CHECK: MOV #200,R1
MOV #3$,R2
1$: CLR (R2)+
SOB R1,1$
2$: INCB 3$(R0)
JSR PC,SUMSQ
TST 3$(R0)
BEQ 2$
DEC R0
RTS PC
3$: .BLKW 200
; LET R0 = SUM OF SQUARES OF DIGITS OF R0
SUMSQ: CLR R2
1$: MOV #-1,R1
2$: INC R1
SUB #12,R0
BCC 2$
ADD #12,R0
MOVB 3$(R0),R0
ADD R0,R2
MOV R1,R0
BNE 1$
MOV R2,R0
RTS PC
3$: .BYTE ^D 0,^D 1,^D 4,^D 9,^D16
.BYTE ^D25,^D36,^D49,^D64,^D81
; PRINT NUMBER IN R0 AS DECIMAL.
PR0: MOV #4$,R1
1$: MOV #-1,R2
2$: INC R2
SUB #12,R0
BCC 2$
ADD #72,R0
MOVB R0,-(R1)
MOV R2,R0
BNE 1$
3$: MOVB (R1)+,R0
.TTYOUT
BNE 3$
RTS PC
.ASCII /...../
4$: .BYTE 15,12,0
.END HAPPY</syntaxhighlight>
{{out}}
<pre>1
7
10
13
Line 4,411 ⟶ 4,647:
{{out}}
<pre>1 7 10 13 19 23 28 31 </pre>
=={{header|Maxima}}==
<syntaxhighlight lang="maxima">
/* Function that decomposes te number into a list */
decompose(N) := block(
digits: [],
while N > 0 do
(remainder: mod(N, 10),
digits: cons(remainder, digits),
N: floor(N/10)),
digits
)$
/* Function that given a number returns the sum of their digits */
sum_squares_digits(n):=block(
decompose(n),
map(lambda([x],x^2),%%),
apply("+",%%))$
/* Predicate function based on the task iterated digits squaring */
happyp(n):=if n=1 then true else if n=89 then false else block(iter:n,while not member(iter,[1,89]) do iter:sum_squares_digits(iter),iter,if iter=1 then true)$
/* Test case */
/* First eight happy numbers */
block(
happy:[],i:1,
while length(happy)<8 do (if happyp(i) then happy:endcons(i,happy),i:i+1),
happy);
</syntaxhighlight>
{{out}}
<pre>
[1,7,10,13,19,23,28,31]
</pre>
=={{header|MAXScript}}==
Line 4,521 ⟶ 4,790:
{{out}}
<pre>First 8 happy numbers: [1, 7, 10, 13, 19, 23, 28, 31]</pre>
=={{header|Miranda}}==
<syntaxhighlight lang="miranda">main :: [sys_message]
main = [Stdout (lay (map show (take 8 happynumbers)))]
happynumbers :: [num]
happynumbers = filter ishappy [1..]
ishappy :: num->bool
ishappy n = 1 $in loop (iterate sumdigitsquares n)
sumdigitsquares :: num->num
sumdigitsquares 0 = 0
sumdigitsquares n = (n mod 10)^2 + sumdigitsquares (n div 10)
loop :: [*]->[*]
loop = loop' []
where loop' mem (a:as) = mem, if a $in mem
= loop' (a:mem) as, otherwise
in :: *->[*]->bool
in val [] = False
in val (a:as) = True, if a=val
= val $in as, otherwise</syntaxhighlight>
{{out}}
<pre>1
7
10
13
19
23
28
31</pre>
=={{header|ML}}==
Line 4,960 ⟶ 5,262:
>happyNum(8)
[1, 7, 10, 13, 19, 23, 28, 31]
</pre>
=={{header|Ol}}==
<syntaxhighlight lang="Scheme">
(define (number->list num)
(let loop ((num num) (lst #null))
(if (zero? num)
lst
(loop (quotient num 10) (cons (remainder num 10) lst)))))
(define (** x) (* x x))
(define (happy? num)
(let loop ((num num) (seen #null))
(cond
((= num 1) #true)
((memv num seen) #false)
(else
(loop (apply + (map ** (number->list num)))
(cons num seen))))))
(display "happy numbers: ")
(let loop ((n 1) (count 0))
(unless (= count 8)
(if (happy? n)
then
(display n) (display " ")
(loop (+ n 1) (+ count 1))
else
(loop (+ n 1) count))))
(print)
</syntaxhighlight>
<pre>
happy numbers: 1 7 10 13 19 23 28 31
</pre>
Line 6,094 ⟶ 6,430:
There's more than one way to do it...
=={{header|Refal}}==
<syntaxhighlight lang="refal">$ENTRY Go {
= <ShowFirst 8 Happy 1>;
};
ShowFirst {
0 s.F s.I = ;
s.N s.F s.I, <Mu s.F s.I>: T =
<Prout s.I>
<ShowFirst <- s.N 1> s.F <+ s.I 1>>;
s.N s.F s.I =
<ShowFirst s.N s.F <+ s.I 1>>;
};
Happy {
1 e.X = T;
s.N e.X s.N e.Y = F;
s.N e.X = <Happy <SqDigSum s.N> s.N e.X>;
};
SqDigSum {
0 = 0;
s.N, <Symb s.N>: s.Ds e.Rs,
<Numb s.Ds>: s.D,
<Numb e.Rs>: s.R =
<+ <* s.D s.D> <SqDigSum s.R>>;
};</syntaxhighlight>
{{out}}
<pre>1
7
10
13
19
23
28
31</pre>
=={{header|Relation}}==
Line 6,142 ⟶ 6,515:
=={{header|REXX}}==
<syntaxhighlight lang="rexx">/*REXX program computes and displays a specified range of happy numbers. */
Call time 'R'
linesize=80
Parse Arg low high /* obtain range of happy numbers */
If low='?' Then Call help
If low='' Then low=10
If high='' Then
Parse Value 1 low With low high
Do i=0 To 9 /*build a squared decimal digit table. */
square.i=i*i
End
happy.=0 /* happy.m=1 - m is a happy number */
unhappy.=0 /* unhappy.n=1 - n is an unhappy number*/
hapn=0 /* count of the happy numbers */
ol=''
Do n=1 While hapn<high /* test integers starting with 1 */
If unhappy.n Then /* if n is unhappy, */
Iterate /* then try next number */
work=n
suml='' /* list of computed sums */
Do Forever
sum=0
Do length(work) /* compute sum of squared digits */
Parse Var work digit +1 work
sum=sum+square.digit
End
Select
When unhappy.sum |, /* sum is known to be unhappy */
wordpos(sum,suml)>0 Then Do /* or was already encountered */
-- If wordpos(sum,suml)>0 Then say 'Loop' n':' suml sum
-- If n<7 Then say n':' suml sum
unhappy.n=1 /* n is unhappy */
Call set suml /* amd so are all sums so far */
Iterate n
End
When sum=1 Then Do /* we reached sum=1 */
hapn+=1 /* increment number of happy numbers */
happy.n=1 /* n is happy */
If hapn>=low Then /* if it is in specified range */
Call out n /* output it */
If hapn=high Then /* end of range reached */
Leave n /* we are done */
Iterate n /* otherwise proceed */
End
Otherwise Do /* otherwise */
suml=suml sum /* add sum to list of sums */
work=sum /* proceed with the new sum */
End
End
End
End
If ol>'' Then /* more output data */
Say strip(ol) /* write to console */
-- Say time('E')
Exit
set:
Parse Arg list
Do While list<>''
Parse Var list s list
unhappy.s=1
End
Return
out:
Parse Arg hn
If length(ol hn)>linesize Then Do /* if it does not fit */
End
Else /* otherwise
ol=ol hn /* append is to the output line */
Return
help:
Say 'rexx hno low high show happy numbers from index low to high'
Exit
</syntaxhighlight>
{{out}}
<pre>
K:\_B\HN>rexx hno ?
rexx hno n compute and show the first n happy numbers
rexx hno low high show happy numbers from index low to
K:\_B\HN>rexx hno 8
1 7 10 13 19 23 28 31
K:\_B\HN>rexx hno 1000 1003
6899 6904 6917 6923
</pre>
=={{header|Ring}}==
Line 6,369 ⟶ 6,645:
</pre>
=={{header|RPL}}==
{{works with|Halcyon Calc|4.2.7}}
≪ { } SWAP '''DO'''
SWAP OVER + 0 ROT
'''DO'''
MANT RND DUP IP SQ ROT + SWAP FP
'''UNTIL''' DUP NOT '''END'''
DROP
'''UNTIL''' DUP2 POS '''END'''
SWAP DROP 1 ==
≫
'HAPY?' STO
≪ { } 0 '''DO'''
1 + '''IF''' DUP HAPY? '''THEN''' SWAP OVER + SWAP '''END'''
'''UNTIL''' OVER SIZE 8 == '''END'''
≫ EVAL
{{out}}
<pre>
1: { 1 7 10 13 19 23 28 31 }
</pre>
=={{header|Ruby}}==
{{works with|Ruby|2.1}}
Line 6,989 ⟶ 7,286:
31 is a happy number
</pre>
=={{header|Uiua}}==
{{works with|Uiua|0.10.0-dev.1}}
<syntaxhighlight lang="Uiua">
HC ← /+ⁿ2≡⋕°⋕ # Happiness calc = sum of squares of digits
IH ← |2 memo⟨IH ⊙⊂.|=1⟩∊,, HC # Apply HC until seen value recurs
Happy ← ⟨0◌|∘⟩IH : [1] . # Pre-load `seen` with 1. Return start number or 0
# Brute force approach isn't too bad with memoisation even for high bounds.
↙8⊚>0≡Happy⇡10000
# But iterative approach is still much faster
NH ← |1 ⟨NH|∘⟩≠0Happy.+1 # Find next Happy number
⇌[⍥(NH.) 7 1]
</syntaxhighlight>
=={{header|UNIX Shell}}==
Line 7,098 ⟶ 7,410:
</pre>
=={{header|V (Vlang)}}==
{{trans|go}}
<syntaxhighlight lang="v (vlang)">fn happy(h int) bool {
mut m := map[int]bool{}
mut n := h
Line 7,133 ⟶ 7,445:
=={{header|Wren}}==
{{trans|Go}}
<syntaxhighlight lang="
var m = {}
while (n > 1) {
|