DEV Community

chenge
chenge

Posted on • Updated on

My Solutions for Perfect Number in Several Languages

There's a warm discuss in post Write a script to find "Perfect Numbers" . Here's my solutions.

Ruby

def sum_divisions(n)
  (1...n).select{|i| n % i == 0}.sum
end

def perfect_number?(n)
  n == sum_divisions(n)
end

(1..10_000).each do |i|
  puts "#{i} is perfect" if perfect_number?(i)
end

Node

const sum = (accumulator, currentValue) => accumulator + currentValue;

function range(size, startAt = 0) {
  return [...Array(size).keys()].map(i => i + startAt);
}

function sumDivisions(n){
  arr = range(n-1, startAt=1).filter(x => n % x == 0)
  return arr.reduce(sum, 0);
}

function is_perfect_number(n){
  return sumDivisions(n) == n
}

range(10000, 1).forEach(function(x){
  if(is_perfect_number(x)){
    console.log(x);
  }
})

Go

package main

import (
  "fmt"
)

func sum_divisions(n int) int {
  sum := 0
  for i := 1; i < n; i++ {
    if n % i == 0 {
      sum += i
    }
  }
  return sum
}

func is_perfect(n int) bool {
  return n == sum_divisions(n)
}

func main() {
  for i := 1; i <= 10000; i++ {
    if is_perfect(i) {
      fmt.Println(i)
    }
  }
}

Rust


fn main(){
  let perfects = (1..10_000).filter(|x| is_perfect(*x) );
  for x in perfects {
    println!("{}", x)
  }
}

fn is_perfect(n: i32) -> bool{
  n == sum_divisions(n)
}

fn sum_divisions(n: i32) -> i32{
  (1..n).filter(|x| n % x == 0).sum()
}

Elixir

defmodule Play do
  def perfect?(n) do
    n == sum_divisions(n)
  end

  defp sum_divisions(n) do
    Enum.filter(1..(n-1), fn(x) -> rem(n, x) == 0 end)
    |> Enum.sum
  end
end

Enum.each(2..10_000, fn(x) -> if Play.perfect?(x), do: IO.puts(x) end)

Clojure


(defn sum_divisions [x]
  (apply + 
    (filter #(= 0 (rem x %)) (range 1 x))))

(defn is_perfect [x]
  (= x (sum_divisions x)))

(doseq [i (range 1 10000)] 
  (if (is_perfect i) (println i)))

v2, thanks @jcsvveiga

...
(doseq [ i (range 1 10000)
        :when (is_perfect i) ] 
  (println i) )

End

I'm new to Node, Go, Rust, Elixir and Clojure, if you have better code, welcome comment.

Happy playing!

Top comments (4)

Collapse
 
grayjack profile image
GrayJack • Edited

In rust, there 2 idiomatic way to do the main()

Your version is idiomatic, but there also this way:

fn main(){
  (1..10_000).filter(|x| is_perfect(*x)).for_each(|x| println!("{}", x));
}

For something simple like this, I would use this version

Collapse
 
chenge profile image
chenge

This is like Ruby, nice.

Collapse
 
jcsvveiga profile image
João Veiga

In the Clojure example, you can move the if into :when clojuredocs.org/clojure.core/doseq...

Collapse
 
chenge profile image
chenge

thanks, that's better.