Created
September 3, 2014 02:50
-
-
Save archer884/ee38d5560dc65bfa1076 to your computer and use it in GitHub Desktop.
Episode stitcher togetherer
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using System; | |
using System.Collections.Generic; | |
using System.IO; | |
using System.Linq; | |
using System.Text; | |
using System.Text.RegularExpressions; | |
using System.Threading.Tasks; | |
namespace _01_Episodes | |
{ | |
static class Extensions | |
{ | |
public delegate bool TryParseDelegate<T1, T2>(T1 value, out T2 result); | |
public static IEnumerable<T2> TrySelect<T1, T2>(this IEnumerable<T1> collection, TryParseDelegate<T1, T2> tryParse) | |
{ | |
foreach (var item in collection) | |
{ | |
T2 select; | |
if (tryParse(item, out select)) yield return select; | |
} | |
} | |
} | |
class Program | |
{ | |
static void Main(string[] args) | |
{ | |
args = new[] { "data.txt" }; // cheating | |
var parser = new EpisodeDataParser(ParseColonDelimited, ParseNonDelimited); | |
var input = args.Length > 0 && File.Exists(args[0]) | |
? File.ReadLines(args[0]) | |
: ReadStandardInput(); | |
var episodes = input.TrySelect<string, EpisodeData>(parser.TryParse) | |
.OrderBy(e => e.Season) | |
.ThenBy(e => e.Episode); | |
foreach (var episode in episodes) | |
{ | |
Console.WriteLine(episode); | |
} | |
} | |
static IEnumerable<string> ReadStandardInput() | |
{ | |
string input; | |
while(true) | |
if (!String.IsNullOrWhiteSpace(input = Console.ReadLine())) | |
yield return input; | |
else break; | |
} | |
static EpisodeData ParseColonDelimited(string data) | |
{ | |
var tokenDelimitedData = new Regex(@"(\d|\w)+?:(\d|\w)+?(?=\s)"); | |
if (tokenDelimitedData.IsMatch(data)) | |
{ | |
var values = tokenDelimitedData.Match(data).Value.Split(':'); | |
return new EpisodeData() | |
{ | |
Season = Int32.Parse(new String(values[0].SkipWhile(Char.IsLetter).TakeWhile(Char.IsDigit).ToArray())), | |
Episode = Int32.Parse(new String(values[1].SkipWhile(Char.IsLetter).TakeWhile(Char.IsDigit).ToArray())), | |
Title = data, | |
Url = "get real I didn't bother with this", | |
}; | |
} | |
else return null; | |
} | |
static EpisodeData ParseNonDelimited(string data) | |
{ | |
var nonDelimitedData = new Regex(@"(\d)(?=: )"); | |
if (nonDelimitedData.IsMatch(data)) | |
{ | |
var value = nonDelimitedData.Match(data).Value; | |
return new EpisodeData() | |
{ | |
Season = 1, | |
Episode = Int32.Parse(value), | |
Title = data, | |
Url = "still didn't bother with this", | |
}; | |
} | |
else return null; | |
} | |
class EpisodeDataParser | |
{ | |
IList<Func<string, EpisodeData>> Parsers { get; set; } | |
public EpisodeDataParser() | |
{ | |
} | |
public EpisodeDataParser(params Func<string, EpisodeData>[] parsers) | |
{ | |
Parsers = new List<Func<string, EpisodeData>>(parsers); | |
} | |
public bool TryParse(string data, out EpisodeData episodeData) | |
{ | |
episodeData = null; | |
foreach (var parser in Parsers) | |
{ | |
if ((episodeData = parser(data)) != null) | |
return true; | |
} | |
return false; | |
} | |
} | |
class EpisodeData : IEquatable<EpisodeData>, IComparable<EpisodeData> | |
{ | |
public int Season { get; set; } | |
public int Episode { get; set; } | |
public string Title { get; set; } | |
public string Url { get; set; } | |
public EpisodeData() | |
{ | |
} | |
// From http://stackoverflow.com/questions/892618/create-a-hashcode-of-two-numbers | |
public override int GetHashCode() | |
{ | |
return (int)(Season.GetHashCode() ^ RotateLeft(Episode.GetHashCode(), 16)); | |
} | |
private uint RotateLeft(int value, int count) | |
{ | |
uint workingValue = (uint)value; | |
return (workingValue << count) | (workingValue >> (32 - count)); | |
} | |
public bool Equals(EpisodeData other) | |
{ | |
return this.Season == other.Season && this.Episode == other.Episode; | |
} | |
public int CompareTo(EpisodeData other) | |
{ | |
if (this.Season == other.Season) | |
return this.Season.CompareTo(other.Season); | |
else return this.Episode.CompareTo(other.Episode); | |
} | |
public override string ToString() | |
{ | |
return String.Format("{0}:{1} - {2}", Season, Episode, Title); | |
} | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment