C# Algorithms – Usage of Nested Lists and TryGetValue of Dictionary

Since the beginning of the month, I am visiting a course called Algorithms. As far as I have to work with one of the following languages – C#, C++, Java or Python and somehow Python is rather slow for such a course, I have decided to look back at the good old C# language.

c#

The quest for the day was to make something called “Birthday range”. The idea is the following, e.g. this is the input:

	public static void Main ()
	{
		List  liBirthdays = new List (new int[]{1,1,1,3,4,5,6,6,6,6,7,10,100,100,300,300,301});
		List<list> liRanges = new List<list> 
		{
			new List{1,100},   //14
			new List{9,100},   //3
			new List{100,100}, //2
			new List{300,302}, //3

		};
		birthday_count(liBirthdays, liRanges);
	}

You need to take a look at the list liBirthdays and to come up with a solution of how many people have birthdays in the range liRanges. A birthday may be any given value between 0 and 365. E.g., as you may see my comments, in the first range, between day 1 and day 100, the people with a birthday are 14 (each entry in the liBirthdays is a single person). In the second range (9-100), the result is 3. And in total it is 22, because some of the ranges overlap, so I count them once again.

It really seems trivial to be done. If you know how to do it or if you have a lot of experience in C#. Or probably both. 🙂

In my way, I have not written in this language for quite a long time (especially in Mint and in Ubuntu!), thus it was a challenge. The solution of the riddle is the following:

  1. We generate an object with Linq liOriginal, where we count the number of occurrences of each entry of liBirthdays;
  2. We generate a dictionary myDictionary, where we count the number of occurrences of a given date as value and the date as a key.
  3. The we come up with something, that I really like from the ABC analysis – cumulative calculation of all previous values. This calculation is stored for each value in a list liBirthdaysOrdered  at the value position.
  4. At the end we take a look at the list of list (see the long way of initializing something like this in C#, compared to Python) liBirthdays and we start calculating how many of our people have birthdays in a given range.
  5. That is all, the last thing to do is to print the code! 🙂

Here comes the code:

using System;
using System.Collections.Generic;
using System.Linq;

class MainClass
{
	public static void Main ()
	{
		List  liBirthdays = new List (new int[]{1,1,1,3,4,5,6,6,6,6,7,10,100,100,300,300,301});
		List<list> liRanges = new List<list> 
		{
			new List{1,100},   //14
			new List{9,100},   //3
			new List{100,100}, //2
			new List{300,302}, //3

		};
		birthday_count(liBirthdays, liRanges);
	}

	public static void birthday_count(ListliBirthdays, List<list>liRanges)
	{
		Dictionary<int, int=""> myDictionary = new Dictionary<int,int> ();
		List  liBirthdaysOrdered = new List ();
		List  liBirthdaysSum = new List ();

		int iResult = 0;
		var liOriginal = liBirthdays.GroupBy (i => i);
		int iDays = 367;
		int zero = (int)0;
		int iSum = 0;

		foreach (var l in liOriginal) 
		{
			myDictionary.Add (l.Key, l.Count ());
		}

		for (int i = 0; i < iDays; i++) 
		{
			if (myDictionary.TryGetValue (i, out zero)) 
			{
				liBirthdaysOrdered.Add (myDictionary [i]);
			} 
			else 
			{
				liBirthdaysOrdered.Add (0);
			}
		}

		for (int i = 0; i < liBirthdaysOrdered.Count(); i++) 
		{
			iSum += liBirthdaysOrdered [i];
			liBirthdaysSum.Add (iSum);
		}

		foreach (var item in liRanges) {
			int iBottom = liBirthdaysSum [item [0]-1];
			int iTop = liBirthdaysSum [item [1]];
			int position = iTop - iBottom;
			iResult += position;
		}
		Console.WriteLine (iResult);

	}
}

Enjoy it and try to improve it! 🙂