using System.Collections.Generic;
public static void Main()
Console.WriteLine("Test LexicographicToAlphaNumeric output:");
var tests = new string [] {
foreach(var x in tests.Select(x => LexicographicToAlphaNumeric(x)).OrderBy(x => x))
Console.WriteLine("Test Categorized Sorting output:");
var somedata = new List<string> {"<some data>",
" <Animal Name=\"Lion\" Group=\"Feline\" Colour=\"Brown\" />",
" <Animal Name=\"Zebra\" Group=\"Equidae\" Colour=\"Black and White\" />",
" <Animal Name=\"Tuna\" Group=\"Fish\" Colour=\"Gray\" />",
" <Animal Name=\"Horse1\" Group=\"Equidae\" Colour=\"Black\" />",
" <Animal Name=\"Horse10\" Group=\"Equidae\" Colour=\"White\" />",
" <Animal Name=\"Horse2\" Group=\"Equidae\" Colour=\"White\" />",
" <Animal Name=\"Dog20\" Group=\"Canidae\" Colour=\"Black\" />",
" <Animal Name=\"Dog2\" Group=\"Canidae\" Colour=\"Black\" />",
" <Animal Name=\"Cat\" Group=\"Feline\" Colour=\"Various\" />",
" <Animal Name=\"Falcon\" Group=\"Bird 1\" Colour=\"Brown\" />",
" <Animal Name=\"Duck\" Group=\"Bird 2\" Colour=\"White\" />",
" <Animal Name=\"Eagle\" Group=\"Bird 1\" Colour=\"Brown\" />",
" <Animal Name=\"Shark\" Group=\"Fish\" Colour=\"Gray\" />",
" <Animal Name=\"Mouse\" Group=\"Rodent\" Colour=\"Brown\" />",
var sortedData = SortAnimalsWithoutDisturbingTheOtherLines(somedata).ToList();
foreach(var x in sortedData)
public static string LexicographicToAlphaNumeric(string value, int size = 3)
if (String.IsNullOrWhiteSpace(value)) return value;
bool isNumberGroup = false;
return String.Join("", value.Select((c, index) => {
var isNumber = Char.IsDigit(c);
if( isNumber != isNumberGroup)
isNumberGroup = isNumber;
return new { c, isNumber, groupId, index };
.Select(g => g.First().isNumber ? new string(g.Select(x => x.c).ToArray()).PadLeft(size, '0') : new string(g.Select(x => x.c).ToArray())));
public static IEnumerable<string> SortAnimalsWithoutDisturbingTheOtherLines(IEnumerable<string> lines)
string sortSetPrefix = "<Animal Name=";
bool isInSortSet = false;
var groupRegex = new System.Text.RegularExpressions.Regex(@"Group=\""([^\""]*)\""");
var nameRegex = new System.Text.RegularExpressions.Regex(@"Name=\""([^\""]*)\""");
foreach(var line in lines.Select((line, index) =>
var lineInSortSet = line.Trim().StartsWith(sortSetPrefix);
if (lineInSortSet != isInSortSet)
isInSortSet = lineInSortSet;
var groupName = LexicographicToAlphaNumeric(groupRegex.Match(line).Value);
var animalName = LexicographicToAlphaNumeric(nameRegex.Match(line).Value);
return new { line, index, setId, groupName, animalName };
.OrderBy(x => x.setId).ThenBy(x => x.groupName).ThenBy(x => x.animalName).ThenBy(x => x.index)