Skip to content

Instantly share code, notes, and snippets.

@VisualMelon
Created July 24, 2019 11:52
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save VisualMelon/46d8cb1172c642242fb0e8b745230910 to your computer and use it in GitHub Desktop.
Save VisualMelon/46d8cb1172c642242fb0e8b745230910 to your computer and use it in GitHub Desktop.
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Text;
namespace OdometerString
{
[Flags]
public enum CharSets
{
Lowercase,
Uppercase,
Numbers,
Special
}
class BruteForce3
{
private ulong IntPasswordsGenerated = 0;
public char[] CharList = new char[] { 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', '0', '1', '2', '3', '4', '5', '6', '7', '8', '9' };
public List<int> IntList = new List<int> { 0 };
public string GenerateString()
{
string password = "";
ulong _base = (ulong)CharList.Length;
// get the current value, increment the next.
ulong current = IntPasswordsGenerated++;
do
{
password = CharList[current % _base] + password;
current /= _base;
} while (current != 0);
return password;
}
}
class Program
{
static void Main(string[] args)
{
var bf3 = new BruteForce3();
var _charSet = new char[] { 'a', 'b', 'c' };
var odometer = new Odometer(3, 0, _charSet.Length);
for (int i = 0; i < 10; i++)
{
int c0 = 0;
var result = new StringBuilder(odometer.Gears.Count);
do
{
if (c0 < 10)
{
foreach (var gear in odometer.Gears)
{
result.Append(_charSet[(int)gear]);
}
Console.WriteLine(result);
result.Clear();
}
c0++;
} while (!odometer.Increase());
Console.WriteLine(c0);
}
//BenchmarkDotNet.Running.BenchmarkRunner.Run<Bench2>();
}
public static Stopwatch Measure(Action measureAction, Action<Stopwatch> resultAction = null)
{
var stopwatch = new Stopwatch();
stopwatch.Start();
measureAction();
stopwatch.Stop();
resultAction?.Invoke(stopwatch);
return stopwatch;
}
}
public class RolloverCounter
{
private readonly int _min;
private readonly int _max;
private int _value;
public RolloverCounter(int min, int max, int value)
{
_min = min;
_max = max;
_value = value;
}
public RolloverCounter(int min, int max) : this(min, max, min)
{
}
public int Value { get { return _value; } }
// increases the counter and returns true if rolledover
public bool Increase()
{
if (++_value < _max)
{
return false;
}
_value = _min;
return true;
}
// makes things easier
public static explicit operator int (RolloverCounter rolloverCounter)
{
return rolloverCounter._value;
}
}
public class Odometer
{
private readonly int _gearCount;
private readonly int _min;
private readonly int _max;
public Odometer(int gearCount, int min, int max, params int[] gearValues)
{
_gearCount = gearCount;
_min = min;
_max = max;
Gears =
gearValues.Length > 0
// start at the specified state - for multithreading
? gearValues.Select(x => new RolloverCounter(min, max, x)).ToList()
// start at min
: new List<RolloverCounter>(gearCount) { new RolloverCounter(min, max) };
Max = max;
}
public int Max { get; private set; }
public List<RolloverCounter> Gears { get; private set; }
// increases the odometer and returns true if rolledover
public bool Increase()
{
var gear = 0;
while (gear < Gears.Count && Gears[gear].Increase())
{
gear++;
// add new gear
if (Gears.Count - 1 < gear)
{
if (gear < _gearCount)
Gears.Add(new RolloverCounter(_min, _max, _min));
break;
}
};
if (gear == _gearCount)
{
// rollover
Gears.RemoveRange(1, Gears.Count - 1);
return true;
}
else
{
return false;
}
}
}
public class StringGenerator
{
private readonly char[] _charSet;
private static IEnumerable<char> AsciiRange(char start, char end)
{
if (end < start)
throw new ArgumentException("The end character occur after the start characters");
if (end > 127)
throw new ArgumentException("Range must be ascii printable characters");
return Enumerable.Range(start, end - start + 1).Select(c => (char)c);
}
public StringGenerator(CharSets charSets = CharSets.Lowercase)
{
var chars = new List<char>();
if (charSets.HasFlag(CharSets.Lowercase))
{
chars.AddRange(AsciiRange('a', 'z'));
}
if (charSets.HasFlag(CharSets.Uppercase))
{
chars.AddRange(AsciiRange('A', 'Z'));
}
if (charSets.HasFlag(CharSets.Numbers))
{
chars.AddRange(AsciiRange('0', '9'));
}
_charSet = chars.ToArray();
// shorter char set for debugging
//charSet = Enumerable.Range(97, 99 - 97 + 1).Select(c => (char)c).ToArray();
}
public IEnumerable<string> GenerateStringsT3chb0t(int count)
{
var odometer = new Odometer(count, 0, _charSet.Length);
do
{
var result = new StringBuilder(odometer.Gears.Count);
foreach (var gear in odometer.Gears)
{
result.Append(_charSet[(int)gear]);
}
yield return result.ToString();
} while (!odometer.Increase());
}
public IEnumerable<string> GenerateStringsArray1(int count)
{
var odometer = new Odometer(count, 0, _charSet.Length);
var result = new char[1];
do
{
if (result.Length != odometer.Gears.Count)
result = new char[odometer.Gears.Count];
int i = 0;
foreach (var gear in odometer.Gears)
{
result[i++] = _charSet[(int)gear];
}
yield return new String(result);
} while (!odometer.Increase());
}
public IEnumerable<string> GenerateStringsArray2(int count)
{
var odometer = new Odometer(count, 0, _charSet.Length);
var result = new char[count];
do
{
int i = 0;
foreach (var gear in odometer.Gears)
{
result[i++] = _charSet[(int)gear];
}
yield return new String(result, 0, i);
} while (!odometer.Increase());
}
public IEnumerable<string> GenerateStringsStringBuilder(int count)
{
var odometer = new Odometer(count, 0, _charSet.Length);
var result = new StringBuilder(odometer.Gears.Count);
do
{
foreach (var gear in odometer.Gears)
{
result.Append(_charSet[(int)gear]);
}
yield return result.ToString();
result.Clear();
} while (!odometer.Increase());
}
}
public class Bench2
{
public IEnumerable<int> StringLenghts => new [] { /*2, 3,*/ 4 };
[BenchmarkDotNet.Attributes.ParamsSource(nameof(StringLenghts))]
public int StringLength { get; set; }
private int StringCount;
[BenchmarkDotNet.Attributes.GlobalSetup]
public void GlobalSetup()
{
var stringGenerator = new StringGenerator(CharSets.Lowercase | CharSets.Numbers);
var strings = stringGenerator.GenerateStringsT3chb0t(StringLength).ToList();
StringCount = strings.Count;
}
[BenchmarkDotNet.Attributes.Benchmark]
public void Rolfl()
{
int stringCount = StringCount;
var strings2 = new List<string>();
var bruteForce3 = new BruteForce3();
for (var i = 0; i < stringCount; i++)
{
var generatedString = bruteForce3.GenerateString();
strings2.Add(generatedString);
}
}
[BenchmarkDotNet.Attributes.Benchmark]
public void T3chb0t()
{
var stringGenerator = new StringGenerator(CharSets.Lowercase | CharSets.Numbers);
var strings = stringGenerator.GenerateStringsT3chb0t(StringLength).ToList();
}
[BenchmarkDotNet.Attributes.Benchmark]
public void StringBuilder()
{
var stringGenerator = new StringGenerator(CharSets.Lowercase | CharSets.Numbers);
var strings = stringGenerator.GenerateStringsStringBuilder(StringLength).ToList();
}
[BenchmarkDotNet.Attributes.Benchmark]
public void Array1()
{
var stringGenerator = new StringGenerator(CharSets.Lowercase | CharSets.Numbers);
var strings = stringGenerator.GenerateStringsArray1(StringLength).ToList();
}
[BenchmarkDotNet.Attributes.Benchmark]
public void Array2()
{
var stringGenerator = new StringGenerator(CharSets.Lowercase | CharSets.Numbers);
var strings = stringGenerator.GenerateStringsArray2(StringLength).ToList();
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment