Answer: Since we want to try to get to the key with the least number of keystrokes, we need to try to re-use as many numbers as possible from the last entry. So the approach here is to try to find an un-entered number by using as many digits as possible from the last key. In the below example, the key is hard coded as 98345.
class LockerKey
{
private static string key = "98345";
private static string sequence;
private static int numKeysEntered;
private static int numComparisonsMade;
private static Dictionary<string, bool> elapsedSet = new Dictionary<string, bool>();
/// <summary>
/// This method gets called from an external source to solve for the key
/// Start with 00000 as the key and then try to find the key
/// </summary>
/// <returns>the key</returns>
public static string Solve()
{
sequence = "00000";
elapsedSet.Add(sequence, true);
// Using this as an exit condition
while (numComparisonsMade < 100000)
{
for (int i = 1; i <= 4; i++)
{
var newKeys = GetKeyOfLength(i, 5);
if (newKeys != null)
{
var isMatchFound = EnterKeys(newKeys);
if (isMatchFound)
{
var start = sequence.Length - 5;
var finalKey = sequence.Substring(start, 5);
Console.WriteLine("Match Found: {0}, NumKeyPresses: {1}, NumComparisonsMade: {2}", finalKey, numKeysEntered, numComparisonsMade);
return finalKey;
}
break;
}
}
}
return null;
}
/// <summary>
/// Checks whether the entered value is the key
/// </summary>
/// <returns>true if the last 5 digits make up the key</returns>
private static bool IsKey()
{
numComparisonsMade++;
var start = sequence.Length - 5;
var newKey = sequence.Substring(start, 5);
elapsedSet.Add(newKey, true);
if (newKey == key)
{
return true;
}
return false;
}
/// <summary>
/// Enters keys as represented by the string input
/// </summary>
/// <param name="newKeys"></param>
/// <returns></returns>
private static bool EnterKeys(string newKeys)
{
foreach (char c in newKeys.ToCharArray())
{
sequence += c.ToString();
numKeysEntered++;
}
var rtnValue = IsKey();
return rtnValue;
}
private static string GetKeyOfLength(int length, int maxLength)
{
Console.WriteLine("GetKeyOfLength called with {0} and {1}", length, maxLength);
string appendedString = null;
var maxValue = Math.Pow(10, length);
var reuseLength = maxLength - length;
var reuseStart = sequence.Length - reuseLength;
var reuseString = sequence.Substring (reuseStart, reuseLength);
for (int i = 0; i < maxValue; i++)
{
appendedString = i.ToString().PadLeft(length, '0');
var newKey = reuseString + appendedString;
if (!elapsedSet.Keys.Contains(newKey))
{
Console.WriteLine("AppendedString: {0} New Key: {1} i: {2} maxValue: {3}", appendedString, newKey, i, maxValue);
break;
}
else
{
appendedString = null;
}
}
return appendedString;
}
}
class LockerKey
{
private static string key = "98345";
private static string sequence;
private static int numKeysEntered;
private static int numComparisonsMade;
private static Dictionary<string, bool> elapsedSet = new Dictionary<string, bool>();
/// <summary>
/// This method gets called from an external source to solve for the key
/// Start with 00000 as the key and then try to find the key
/// </summary>
/// <returns>the key</returns>
public static string Solve()
{
sequence = "00000";
elapsedSet.Add(sequence, true);
// Using this as an exit condition
while (numComparisonsMade < 100000)
{
for (int i = 1; i <= 4; i++)
{
var newKeys = GetKeyOfLength(i, 5);
if (newKeys != null)
{
var isMatchFound = EnterKeys(newKeys);
if (isMatchFound)
{
var start = sequence.Length - 5;
var finalKey = sequence.Substring(start, 5);
Console.WriteLine("Match Found: {0}, NumKeyPresses: {1}, NumComparisonsMade: {2}", finalKey, numKeysEntered, numComparisonsMade);
return finalKey;
}
break;
}
}
}
return null;
}
/// <summary>
/// Checks whether the entered value is the key
/// </summary>
/// <returns>true if the last 5 digits make up the key</returns>
private static bool IsKey()
{
numComparisonsMade++;
var start = sequence.Length - 5;
var newKey = sequence.Substring(start, 5);
elapsedSet.Add(newKey, true);
if (newKey == key)
{
return true;
}
return false;
}
/// <summary>
/// Enters keys as represented by the string input
/// </summary>
/// <param name="newKeys"></param>
/// <returns></returns>
private static bool EnterKeys(string newKeys)
{
foreach (char c in newKeys.ToCharArray())
{
sequence += c.ToString();
numKeysEntered++;
}
var rtnValue = IsKey();
return rtnValue;
}
private static string GetKeyOfLength(int length, int maxLength)
{
Console.WriteLine("GetKeyOfLength called with {0} and {1}", length, maxLength);
string appendedString = null;
var maxValue = Math.Pow(10, length);
var reuseLength = maxLength - length;
var reuseStart = sequence.Length - reuseLength;
var reuseString = sequence.Substring (reuseStart, reuseLength);
for (int i = 0; i < maxValue; i++)
{
appendedString = i.ToString().PadLeft(length, '0');
var newKey = reuseString + appendedString;
if (!elapsedSet.Keys.Contains(newKey))
{
Console.WriteLine("AppendedString: {0} New Key: {1} i: {2} maxValue: {3}", appendedString, newKey, i, maxValue);
break;
}
else
{
appendedString = null;
}
}
return appendedString;
}
}
No comments:
Post a Comment
Comments