Narcissistic decimal number: Difference between revisions

Content added Content deleted
(add OCaml)
(→‎OCaml: speedup by 4.5 with pre-calculated powers)
Line 3,210: Line 3,210:


=={{header|OCaml}}==
=={{header|OCaml}}==
===Exhaustive search (integer series)===
;Exhaustive search (integer series)
<syntaxhighlight lang="ocaml">(* speed-optimized exponentiation; doesn't support exponents < 1 *)
<syntaxhighlight lang="ocaml">let narcissistic =
let rec pow b n =
let rec next n l p () =
let rec digit_pow_sum a n =
if n land 1 = 0
then if n = 2 then b * b else pow (b * b) (n lsr 1)
if n < 10 then a + p.(n) else digit_pow_sum (a + p.(n mod 10)) (n / 10)
in
else if n = 1 then b else b * pow (b * b) (n lsr 1)
if n = l then next n (l * 10) (Array.mapi ( * ) p) ()

else if n = digit_pow_sum 0 n then Seq.Cons (n, next (succ n) l p)
let is_narcissistic n =
else next (succ n) l p ()
let rec aux x e =
if x < 10
then pow x e, e
else let n, l = aux (x / 10) (succ e) in n + pow (x mod 10) l, l
in
in
n = fst (aux n 1)
next 0 10 (Array.init 10 Fun.id)


let () =
let () =
narcissistic |> Seq.take 25 |> Seq.iter (Printf.printf " %u") |> print_newline</syntaxhighlight>
Seq.(ints 0 |> filter is_narcissistic |> take 25 |> map string_of_int)
|> List.of_seq |> String.concat " " |> print_endline</syntaxhighlight>
{{out}}
{{out}}
<pre>0 1 2 3 4 5 6 7 8 9 153 370 371 407 1634 8208 9474 54748 92727 93084 548834 1741725 4210818 9800817 9926315</pre>
<pre> 0 1 2 3 4 5 6 7 8 9 153 370 371 407 1634 8208 9474 54748 92727 93084 548834 1741725 4210818 9800817 9926315</pre>


=={{header|Oforth}}==
=={{header|Oforth}}==