Problem:
Euler's Phi Function

For given integer n, count the totatives of n, that is, the positive integers less than or equal to n that are relatively prime to n.

Input

n

An integer n (1 ≤ n ≤ 1000000000).

Output

The number of totatives in a line.

Sample Input 1

6

Sample Output 1

2

Sample Input 2

1000000

Sample Output 2

400000

Solution in Scala (judge verdict: Accepted)

object Main extends App {
  val n = io.StdIn.readInt()
  println(phi(n))

  def phi(n: Int): Int =
    if (isPrime(n)) n-1
    else {
      val pfs = primeFactors(n)
      val x = pfs.foldLeft(n.toDouble)((acc, e) => (acc*(e-1))/e)
      x.toInt
    }
  def primeFactors(n: Int): Seq[Int] = {
    if (n == 1) Seq()
    else if (isPrime(n)) Seq(n)
    else {
      var x = n
      val p = rho(n)
      if (isPrime(p)) {
        while(x % p == 0) x /= p
        p +: primeFactors(x)
      }
      else {
        val ps = primeFactors(p)
        ps foreach (p => while(x % p == 0) x /= p)
        ps ++ primeFactors(x)
      }
    }
  }
  def rho(n: Int): Int = {
    def f(x: Int, c: Int): Int = (x * x + c) % n
    def loop(x: Int, y: Int, d: Int, c: Int = 1): Int =
      if (d != 1) {
        if (d == n) loop(2,2,1,c+1)
        else d
      }
      else {
        val a = f(x, c)
        val b = f(f(y, c), c)
        loop(a, b, gcd(Math.abs(a-b), n), c)
      }
    if (n % 2 == 0) 2
    else loop(2,2,1)
  }
  def gcd(x: Int, y: Int): Int = {
    if (x < y) gcd(y, x)
    else {
      if (y > 0) {
        val r = x % y
        gcd(y, r)
      } else x
    }
  }
  def isPrime(n: Int): Boolean = Primes.miller_rabin_test(n)
  object Primes {
    private def mod_exp(x: BigInt, n: Int, m: Int): BigInt = {
      def loop(x: BigInt, n: Int, acc: BigInt): BigInt = {
        if (n == 0) acc
        else loop (
          (x * x) % m,
          n >> 1,
          if ((n & 1) == 1) (acc * x) % m else acc
        )
      }
      loop(x,n,1)
    }
    private def div_pow_2(d: Int, s: Int = 0): (Int, Int) ={
      if ((d % 2) != 0) (d,s)
      else div_pow_2(d/2, s+1)
    }

    private def miller_rabin(n: Int, a: Int): Boolean = {
      val (d,s): (Int, Int) = div_pow_2(n-1)
      val a_exp_d: BigInt = mod_exp(a,d,n)
      def double(x: BigInt): BigInt = mod_exp(x,2,n)
      def loop(e: BigInt, i: Int): Boolean = {
        if (i == 0) false
        else if (e == n-1) true
        else loop(double(e), i-1)
      }
      a_exp_d == 1 || loop(a_exp_d, s)
    }
    def miller_rabin_test(n: Int, k: Int = 20): Boolean = {
      def loop(i: Int): Boolean = {
        if (i == 0) true
        else {
          val a = scala.util.Random.nextInt(n-1)+1
          if (miller_rabin(n,a)) loop(i-1)
          else false
        }
      }
      if (n < 2) false
      else loop(k)
    }
  }
}