# Ways to form n/2 pairs such that difference of pairs is minimum

Given an array arr of N integers, the task is to split the elements of the array into N/2 pairs (each pair having 2 elements) such that the absolute difference between two elements of any pair is as minimum as possible.
Note: N will always be even.

Examples:

Input: arr[] = {1, 7, 3, 8}
Output: 1
There is only one way to form pairs with
minimum difference, (7, 8) and (1, 3).

Input: arr[] = {1, 1, 1, 1, 2, 2, 2, 2}
Output: 9
Here all elements with value 2 will pair amongst themselves (3 ways possible) and all elements with value 1 will make pairs between them (3 ways possible)
Therefore, number of ways = 3 * 3 = 9

Input: arr[] = {2, 3, 2, 2}
Output: 3

## Recommended: Please try your approach on {IDE} first, before moving on to the solution.

Approach: This problem involves the fundamental principle of counting and some basic understanding of permutations and combinations.

Before going any further, let’s count the number of ways for the array = [3, 3]
Answer = 1, since only 1 combination is possible.
Now, lets modify the array to [3, 3, 3, 3]. The ways for this as discussed in the above examples are:

(1, 2), (3, 4)
(1, 3), (2, 4)
(1, 4), (2, 3)

Further modifying the array to [3, 3, 3, 3, 3, 3]

(1, 2), (3, 4), (5, 6)
(1, 2), (3, 5), (4, 6)
(1, 2), (3, 6), (4, 5)
(1, 3), (2, 4), (5, 6)
(1, 3), (2, 5), (4, 6)
(1, 3), (2, 6), (4, 5)
(1, 4), (2, 3), (5, 6)
(1, 4), (2, 5), (3, 6)
(1, 4), (2, 6), (3, 5)
(1, 5), (2, 3), (4, 6)
(1, 5), (2, 4), (3, 6)
(1, 5), (2, 6), (3, 4)
(1, 6), (2, 3), (4, 5)
(1, 6), (2, 4), (3, 5)
(1, 6), (2, 5), (3, 4)

Here we obtain a generalized result by simple observation. If there are K elements in the array that have the same value and K is even, then the number of ways to form pairs amongst them:

For size 2, count = 1 (1)
For size 4, count = 3 (1 * 3)
For size 6, count = 15 (1 * 3 * 5)
And so on.
Hence, number of ways to form pairs for size K where K is even = 1 * 3 * 5 * …. * (K-1)

We can precompute this result as follows. Let ways[] be the array such that ways[i] stores the number of ways for size ‘i’.

ways[2] = 1;
for(i = 4; i < 1e5 + 1; i += 2)
ways[i] = ways[i – 2] * (i – 1);

For example, we consider array [3, 3, 3, 3, 3]
To compute the number of ways, we fix the first element with any of the remaining 5.
So we form one pair. Now 4 elements are left that can be paired in ways[4] ways.
So number of ways would be 5 * ways[4].

Now, it may not be necessary that counts may always be even in number. Therefore, if need to solve this for a general array, we need to do two things.

1. Sort the array in ascending order.
2. Analyze the count of each group having the same value.

Let our array = [2, 3, 3, 3, 3, 4, 4, 4, 4, 4]. This array is sorted.

• Considering element with value 4. Since there are 5 elements, 4 elements will pair amongst themselves in ways[4] ways. The left out element can be chosen in 5 ways. The element left will have to pair with an element with value 3. This happens in 4 ways since there are 4 elements with value 3. Therefore, one element of value 3 will be reserved to pair with an element of 4. So 3 elements with value 3 remain. 2 will pair amongst themselves in ways[2] ways and one 1 will pair with the element with value 2 in 1 way. Again, the lone element will be selected in 3 ways.
• Therefore from point 1, number of ways will be :
• ways[4] * 5 * 4 * ways[2] * 3 * 1 = 180

Below is the implementation of the above approach:

## C++

 `// C++ implementation of the above approach ` `#include ` ` `  `#define mp make_pair ` `#define pb push_back ` `#define S second ` `#define ll long long ` ` `  `using` `namespace` `std; ` ` `  `// Using mod because the number ` `// of ways might be very large ` `const` `int` `mod = 1000000007; ` ` `  `const` `int` `MAX = 100000; ` ` `  `// ways is serving the same ` `// purpose as discussed ` `ll ways[MAX + 1]; ` ` `  `void` `preCompute() ` `{ ` `    ``// pairing up zero people ` `    ``// requires one way. ` `    ``ways[0] = 1LL; ` `    ``ways[2] = 1LL; ` `    ``for` `(``int` `i = 4; i <= MAX; i += 2) { ` `        ``ways[i] = (1LL * (i - 1) * ways[i - 2]) % mod; ` `    ``} ` `} ` ` `  `void` `countWays(``int``* arr, ``int` `n) ` `{ ` ` `  `    ``// map count stores count of s. ` `    ``map<``int``, ``int``> count; ` `    ``for` `(``int` `i = 0; i < n; i++) ` `        ``count[arr[i]]++; ` ` `  `    ``vector > count_vector; ` `    ``map<``int``, ``int``>::iterator it; ` `    ``for` `(it = count.begin(); it != count.end(); it++) { ` `        ``count_vector.pb(mp(it->first, it->second)); ` `    ``} ` ` `  `    ``// vector count_vector stores a ` `    ``// pair < value, count of value> ` ` `  `    ``// sort according to value ` `    ``sort(count_vector.begin(), count_vector.end()); ` ` `  `    ``ll ans = 1; ` ` `  `    ``// Iterating backwards. ` `    ``for` `(``int` `i = count_vector.size() - 1; i > 0; i--) { ` ` `  `        ``int` `current_count = count_vector[i].S; ` `        ``int` `prev_count = count_vector[i - 1].S; ` ` `  `        ``// Checking if current count is odd. ` `        ``if` `(current_count & 1) { ` ` `  `            ``// if current count = 5, multiply ans by ways[4]. ` `            ``ans = (ans * ways[current_count - 1]) % mod; ` ` `  `            ``// left out person will be selected ` `            ``// in current_count ways ` `            ``ans = (ans * current_count) % mod; ` ` `  `            ``// left out person will pair with previous ` `            ``//  person in previous_count ways ` `            ``ans = (ans * prev_count) % mod; ` ` `  `            ``/* if previous count is odd, ` `             ``* then multiply answer by ways[prev_count-1]. ` `             ``* since one has already been reserved, ` `             ``* remaining will be even. ` `             ``* reduce prev_count = 0, since we don't need it now.*/` `            ``if` `(prev_count & 1) { ` `                ``ans = (ans * ways[prev_count - 1]) % mod; ` `                ``count_vector[i - 1].S = 0; ` `            ``} ` `            ``else` `{ ` ` `  `                ``/* if prev count is even, one will be reserved, ` `                 ``* therefore decrement by 1. ` `                 ``* In the next iteration, prev_count will become odd ` `                 ``* and it will be handled in the same way.*/` `                ``count_vector[i - 1].S--; ` `            ``} ` `        ``} ` `        ``else` `{ ` ` `  `            ``/* if current count is even, ` `             ``* then simply multiply ways[current_count] ` `             ``* to answer.*/` `            ``ans = (ans * ways[current_count]) % mod; ` `        ``} ` `    ``} ` ` `  `    ``/* multiply answer by ways[first__count] since ` `       ``that is left out, after iterating the array.*/` `    ``ans = (ans * ways[count_vector[0].S]) % mod; ` `    ``cout << ans << ``"\n"``; ` `} ` ` `  `// Driver code ` `int` `main() ` `{ ` `    ``preCompute(); ` `    ``int` `arr[] = { 2, 3, 3, 3, 3, 4, 4, 4, 4, 4 }; ` `    ``int` `n = ``sizeof``(arr) / ``sizeof``(arr[0]); ` `    ``countWays(arr, n); ` `    ``return` `0; ` `} `

## Python3

 `# Python3 implementation of the  ` `# above approach  ` `from` `collections ``import` `defaultdict ` ` `  `# Using mod because the number  ` `# of ways might be very large  ` `mod ``=` `1000000007` `MAX` `=` `100000` ` `  `# ways is serving the same  ` `# purpose as discussed  ` `ways ``=` `[``None``] ``*` `(``MAX` `+` `1``)  ` ` `  `def` `preCompute():  ` ` `  `    ``# pairing up zero people  ` `    ``# requires one way.  ` `    ``ways[``0``] ``=` `1` `    ``ways[``2``] ``=` `1` `    ``for` `i ``in` `range``(``4``, ``MAX` `+` `1``, ``2``):  ` `        ``ways[i] ``=` `((``1` `*` `(i ``-` `1``) ``*`  `                    ``ways[i ``-` `2``]) ``%` `mod) ` ` `  `def` `countWays(arr, n):  ` ` `  `    ``# map count stores count of s.  ` `    ``count ``=` `defaultdict(``lambda``:``0``) ` `    ``for` `i ``in` `range``(``0``, n):  ` `        ``count[arr[i]] ``+``=` `1` ` `  `    ``count_vector ``=` `[]  ` `    ``for` `key ``in` `count:  ` `        ``count_vector.append([key, count[key]])  ` ` `  `    ``# vector count_vector stores a  ` `    ``# pair < value, count of value>  ` ` `  `    ``# sort according to value  ` `    ``count_vector.sort()  ` `    ``ans ``=` `1` ` `  `    ``# Iterating backwards.  ` `    ``for` `i ``in` `range``(``len``(count_vector) ``-` `1``, ``-``1``, ``-``1``):  ` ` `  `        ``current_count ``=` `count_vector[i][``1``]  ` `        ``prev_count ``=` `count_vector[i ``-` `1``][``1``]  ` ` `  `        ``# Checking if current count is odd.  ` `        ``if` `current_count & ``1``:  ` ` `  `            ``# if current count = 5, multiply ` `            ``# ans by ways[4].  ` `            ``ans ``=` `(ans ``*` `ways[current_count ``-` `1``]) ``%` `mod  ` ` `  `            ``# left out person will be selected  ` `            ``# in current_count ways  ` `            ``ans ``=` `(ans ``*` `current_count) ``%` `mod  ` ` `  `            ``# left out person will pair with previous  ` `            ``# person in previous_count ways  ` `            ``ans ``=` `(ans ``*` `prev_count) ``%` `mod  ` ` `  `            ``# if previous count is odd,  ` `            ``# then multiply answer by ways[prev_count-1].  ` `            ``# since one has already been reserved,  ` `            ``# remaining will be even.  ` `            ``# reduce prev_count = 0, since we ` `            ``# don't need it now. ` `            ``if` `prev_count & ``1``: ` `                ``ans ``=` `(ans ``*` `ways[prev_count ``-` `1``]) ``%` `mod  ` `                ``count_vector[i ``-` `1``][``1``] ``=` `0` `             `  `            ``else``: ` ` `  `                ``# if prev count is even, one will be  ` `                ``# reserved, therefore decrement by 1.  ` `                ``# In the next iteration, prev_count  ` `                ``# will become odd and it will be  ` `                ``# handled in the same way. ` `                ``count_vector[i ``-` `1``][``1``] ``-``=` `1` `             `  `        ``else``: ` ` `  `            ``# if current count is even, then simply ` `            ``# multiply ways[current_count] to answer. ` `            ``ans ``=` `(ans ``*` `ways[current_count]) ``%` `mod  ` `         `  `    ``# multiply answer by ways[first__count] since  ` `    ``# that is left out, after iterating the array. ` `    ``ans ``=` `(ans ``*` `ways[count_vector[``0``][``1``]]) ``%` `mod  ` `    ``print``(ans)  ` ` `  `# Driver code  ` `if` `__name__ ``=``=` `"__main__"``: ` ` `  `    ``preCompute()  ` `    ``arr ``=` `[``2``, ``3``, ``3``, ``3``, ``3``, ``4``, ``4``, ``4``, ``4``, ``4``]  ` `    ``n ``=` `len``(arr) ` `    ``countWays(arr, n)  ` `     `  `# This code is contributed by Rituraj Jain `

Output:

```180
```

My Personal Notes arrow_drop_up

An enthusiastic Java and web developer with a little affinity for tea, cricket, English, etymology, and reading

If you like GeeksforGeeks and would like to contribute, you can also write an article using contribute.geeksforgeeks.org or mail your article to contribute@geeksforgeeks.org. See your article appearing on the GeeksforGeeks main page and help other Geeks.

Please Improve this article if you find anything incorrect by clicking on the "Improve Article" button below.