Problem:
Score : 300 points

Problem Statement

You are given N real values A_1, A_2, \ldots, A_N.
Compute the number of pairs of indices (i, j)
such that i < j and the product A_i \cdot A_j is integer.

Constraints

2 \leq N \leq 200\,000

0 < A_i < 10^4

A_i is given with at most 9 digits after the decimal.

Input

Input is given from Standard Input in the following format.

N
A_1
A_2
\vdots
A_N

Output

Print the number of pairs with integer product A_i \cdot A_j (and i < j).

Sample Input 1

5
7.5
2.4
17.000000001
17
16.000000000

Sample Output 1

3

There are 3 pairs with integer product:

7.5 \cdot 2.4 = 18

7.5 \cdot 16 = 120

17 \cdot 16 = 272

Sample Input 2

11
0.9
1
1
1.25
2.30000
5
70
0.000000001
9999.999999999
0.999999999
1.000000001

Sample Output 2

8

Solution in C# (.NET Core 3.1.201) (judge verdict: Wrong Answer)

using System;
using System.Collections.Generic;

namespace ConsoleApp1
{
    class Program
    {
        static void Main(string[] args)
        {
            int N;
            Dictionary<Tuple<int, int>, int> bucket = new Dictionary<Tuple<int, int>, int>();
            N = Convert.ToInt32(Console.ReadLine());
            numNode a;
            for (int i = 0; i < N; i++)
            {
                var theNumber = Console.ReadLine();
                var pos = theNumber.IndexOf('.');
                if (pos == -1)
                {
                    a = new numNode(theNumber);
                }
                else
                {
                    var intpart = Convert.ToInt64(theNumber.Substring(0, pos));
                    var powOfDen = Convert.ToInt64(Math.Pow(10, Convert.ToDouble(theNumber.Length - pos - 1)));
                    var decipart = Convert.ToInt64(theNumber.Substring(pos + 1));
                    a = new numNode(intpart * powOfDen + decipart, powOfDen);
                }
                if (bucket.ContainsKey(a.GetTuple()))
                {
                    bucket[a.GetTuple()] += 1;
                }
                else
                {
                    bucket[a.GetTuple()] = 1;
                }
            }

            Int64 s = 0;
            foreach (var it in bucket.Keys)
            {
                var x1 = it.Item1;
                var y1 = it.Item2;
                var r1 = bucket[it];
                foreach (var it2 in bucket.Keys)
                {
                    var x2 = it2.Item1;
                    var y2 = it2.Item2;
                    var r2 = bucket[it2];
                    if (x1 + x2 >= 0 && y1 + y2 >= 0)
                    {
                        if (lessThan(it , it2))
                        {
                            s += r1 * r2;
                        }
                        else if (it == it2)
                        {
                            s += (r1 * (r1 - 1)) / 2;
                        }
                    }
                }
            }
            Console.WriteLine(s);
        }
        private static bool lessThan(Tuple<int,int> a,Tuple<int,int> b)
        {
            if(a.Item1==b.Item1)
            {
                return a.Item2 < b.Item2;
            }
            else
            {
                return a.Item1 < b.Item1;
            }
        }
       
    }
    
    
    
    class numNode
    {
        private int c2 { get; set; }
        private int c5 { get; set; }

        public numNode() { }

        public numNode(Int64 num, Int64 den)
        {
            c2 = 0;
            while (num % 2 == 0)
            {
                c2++;
                num /= 2;
            }
            while (den % 2 == 0)
            {
                c2--;
                den /= 2;
            }
            c5 = 0;
            while (num % 5 == 0)
            {
                c5++;
                num /= 5;
            }
            while (den % 5 == 0)
            {
                c5--;
                den /= 5;
            }
        }
        public numNode(string v)
        {
            int num = Convert.ToInt32(v);
            c2 = 0;
            while (num % 2 == 0)
            {
                c2++;
                num /= 2;
            }
            c5 = 0;
            while (num % 5 == 0)
            {
                c5++;
                num /= 5;
            }
        }
        public Tuple<int, int> GetTuple()
        {
            return new Tuple<int, int>(c2, c5);
        }

    }
}