I have started reading clean code and want to improve my coding practices. Here is my attempt at solving an online puzzle. Please review the code and let me know how could I have written it better in terms of logic, coding practices or any other advice you might have.
Problem Statement
Sherlock is given an array of N integers (\$A_0, A_1 \ldots A_{N-1}\$) by Watson. Now Watson asks Sherlock how many different pairs of indices \$i\$ and \$j\$ exist such that \$i\$ is not equal to \$j\$ but \$A_i\$ is equal to \$A_j\$.
That is, Sherlock has to count the total number of pairs of indices \$(i,j)\$ where \$A_i =Aj\$ AND \$i≠j\$.
Input Format
The first line contains \$T\$, the number of test cases. \$T\$ test cases follow. Each test case consists of two lines; the first line contains an integer \$N\$, the size of array, while the next line contains N space separated integers.
Output Format
For each test case, print the required answer on a different line.
Constraints
\$1≤T≤10\$
\$1≤N≤10^5\$
\$1≤A[i]≤10^6\$
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace NoOfPairsInASet
{
class Solution
{
static Dictionary<Int64, Int64> CountOfElements = new Dictionary<Int64, Int64>();
static Int64 Sum = 0;
static Int64[] data;
static void Main(string[] args)
{
int TestCases = Convert.ToInt32(Console.ReadLine());
//int TestCases = 1;
for (int t = 0; t < TestCases; t++)
{
CalculatePairs();
Console.WriteLine(Sum);
}
}
private static void CalculatePairs()
{
int NoOfElements = Convert.ToInt32(Console.ReadLine());
string Elements = Console.ReadLine();
//int NoOfElements = 3;
//string Elements = "1 1 2 1 2";
string[] ArrayOfElements = Elements.Split(' ');
data = new Int64[ArrayOfElements.Length];
ConvertStringToInt(ArrayOfElements);
GenerateDictionary();
CalculateSum();
}
private static void ConvertStringToInt(string[] ArrayOfElements)
{
for (Int64 i = 0; i < ArrayOfElements.Length; i++)
{
data[i] = Convert.ToInt64(ArrayOfElements[i]);
}
}
private static void GenerateDictionary()
{
CountOfElements.Clear();
int DEFAULTCOUNT = 1;
for (Int64 i = 0; i < data.Length; i++)
{
if (CountOfElements.ContainsKey(data[i]) == true)
{
IncrementCounter(i);
}
else
{
CountOfElements.Add(data[i], DEFAULTCOUNT);
}
}
}
private static void IncrementCounter(Int64 i)
{
Int64 count = CountOfElements[(data[i])];
count++;
CountOfElements[(data[i])] = count;
}
private static void CalculateSum()
{
Sum = 0;
foreach (KeyValuePair<Int64, Int64> item in CountOfElements)
{
if (item.Value > 1)
{
Sum += CalculatePermutationOfValue(item.Value, 2);
}
}
}
private static Int64 CalculatePermutationOfValue(Int64 n, Int64 r)
{
//Int64 P = factorial(n) / factorial(n - r); // with r = 2, this simplifies to n*n-1
Int64 P = n * (n - 1);
return P;
}
//private static Int64 factorial(Int64 n)
//{
// Int64 fact = 1;
// for (Int64 i = n; i >= 1; i--)
// {
// fact = fact * i;
// }
// return fact;
//}
}
}
I have kept the test cases still commented. Is that okay? Also, I have still kept the factorial function as it can be used in the future. Should I remove the factorial function or can I keep it commented?