Problem:
MathJax.Hub.Config({ tex2jax: { inlineMath: [["$","$"], ["\\(","\\)"]], processEscapes: true }});

The Number of Inversions

For a given sequence $A = \{a_0, a_1, ... a_{n-1}\}$, the number of pairs $(i, j)$ where $a_i > a_j$ and $i < j$, is called the number of inversions. The number of inversions is equal to the number of swaps of Bubble Sort defined in the following program:

bubbleSort(A)
cnt = 0 // the number of inversions
for i = 0 to A.length-1
for j = A.length-1 downto i+1
if A[j] < A[j-1]
swap(A[j], A[j-1])
cnt++

return cnt

For the given sequence $A$, print the number of inversions of $A$. Note that you should not use the above program, which brings Time Limit Exceeded.

Input

In the first line, an integer $n$, the number of elements in $A$, is given. In the second line, the elements $a_i$ ($i = 0, 1, .. n-1$) are given separated by space characters.

output

Print the number of inversions in a line.

Constraints

$ 1 \leq n \leq 200,000$

$ 0 \leq a_i \leq 10^9$

$a_i$ are all different

Sample Input 1

5
3 5 2 1 4

Sample Output 1

6

Sample Input 2

3
3 1 2

Sample Output 2

2

Solution in Scala (judge verdict: Accepted)

import scala.io.StdIn

object Main extends App {


  val rn = StdIn.readLine().trim.toInt
  val ina = StdIn.readLine().trim.split(' ').map(_.toInt)
  
  final val infity = Int.MaxValue
  def mergeSort(): Long = {
    @inline def copyToArray(start: Int, end: Int): Array[Int] = {
      val alsize = end - start + 1
      val temp = new Array[Int](alsize)
      Array.copy(ina, start, temp, 0, alsize - 1)
      temp(alsize-1) = infity
      temp
    }

    def merge(left: Int, mid: Int, right: Int): Long ={
      val al = copyToArray(left, mid)
      val ar = copyToArray(mid, right)
      var i = 0
      var j = 0
      var cnt = 0L
      //println("left:" + al.toList)
      //println("right:" + ar.toList)
      (left until right).foreach{ k =>
        if(al(i) <= ar(j)){
          ina(k) = al(i)
          i += 1
        } else {
          ina(k) = ar(j)
          j += 1
          cnt += mid - left - i
        }
      }
      //println("all:" + ar2.toList.mkString(" "))
      cnt
    }

    def innerMergeSort(left: Int, right: Int): Long ={
      
      if(left+1 < right){
        val mid = (left + right) / 2
        val rleft = innerMergeSort(left, mid)
        val rright = innerMergeSort(mid, right)
        val rmerge = merge(left, mid, right)
        
        rleft + rright + rmerge
      } else {
        0L
      }
    }

    innerMergeSort(0, rn)

  }
  
  println(mergeSort)

  
}