Problem:
Score : 400 points

Problem Statement

Takahashi has N sticks that are distinguishable from each other. The length of the i-th stick is L_i.

He is going to form a triangle using three of these sticks. Let a, b, and c be the lengths of the three sticks used. Here, all of the following conditions must be satisfied:

a < b + c

b < c + a

c < a + b

How many different triangles can be formed? Two triangles are considered different when there is a stick used in only one of them.

Constraints

All values in input are integers.

3 \leq N \leq 2 \times 10^3

1 \leq L_i \leq 10^3

Input

Input is given from Standard Input in the following format:

N
L_1 L_2 ... L_N

Constraints

Print the number of different triangles that can be formed.

Sample Input 1

4
3 4 2 1

Sample Output 1

1

Only one triangle can be formed: the triangle formed by the first, second, and third sticks.

Sample Input 2

3
1 1000 1

Sample Output 2

0

No triangles can be formed.

Sample Input 3

7
218 786 704 233 645 728 389

Sample Output 3

23

Solution in C++14 (GCC 5.4.1) (judge verdict: Accepted)

#include <bits/stdc++.h>

using namespace std;

int l[2000+5];

int main(){
    int n,memo,memo1,memo2;
    long long ans=0;

    cin >> n;
    for(int i=0; i<n;i++) cin >> l[i];
    sort(l, l+n);

    for (int a=0; a<n-2; a++){
        for (int b=a+1; b<n-1; b++){
            memo = max(l[a]-l[b],l[b]-l[a]);
            auto lft = upper_bound(l,l+n,memo);
            auto rgt = lower_bound(l,l+n,l[a]+l[b]);
            memo1 = rgt-lft;
            
            if (*rgt == n || memo1<=0 || rgt <= &l[b]) {
            continue; }
            if (lft<=&l[b]) memo1 = rgt-&l[b];
            
    
            /*
            memo1 = lft - &l[0]+1;
            memo2 = rgt - &l[0]+1;
            cout << a << " " << b << " "<<  l[*lft]<< memo1 <<" "<<memo2-memo1<< endl;
            if (memo2 == n || memo2-memo1<=0) {continue; 
            cout<<1111;}
            */
            ans += memo1-1; 
            
        }  
    }

    cout << ans << endl;

 


    return 0;
}