Created
August 19, 2013 17:15
-
-
Save stofte/6271588 to your computer and use it in GitHub Desktop.
ini file serializer
This file contains 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.Linq; | |
using System.Text; | |
using System.Threading.Tasks; | |
using System.Runtime.Serialization; | |
using System.IO; | |
using System.Text.RegularExpressions; | |
using System.Globalization; | |
using System.Collections; | |
using System.Threading; | |
namespace ConsoleApplication2 | |
{ | |
[Serializable] | |
public class IniFile | |
{ | |
public IList<Section> Sections; | |
} | |
[Serializable] | |
public class Section | |
{ | |
public string Title; | |
public IDictionary<string, object> Entries; | |
} | |
class Program | |
{ | |
static void Main(string[] args) | |
{ | |
Thread.CurrentThread.CurrentCulture = CultureInfo.InvariantCulture; | |
var formatter = new CrappyIniFormatter(); | |
var output = new FileStream("foo.ini", FileMode.Create); | |
var inifile = new IniFile { Sections = new List<Section>() }; | |
var entries = new Dictionary<string, object> { | |
{ "foo", 1.2f }, | |
{ "bar", "baz" } | |
}; | |
var section = new Section { Title = "My stuff", Entries = entries }; | |
inifile.Sections.Add(section); | |
formatter.Serialize(output, inifile); | |
output.Close(); | |
var s = new FileStream("foo.ini", FileMode.Open); | |
var t = (IniFile)formatter.Deserialize(s); | |
} | |
} | |
public class CrappyIniFormatter : IFormatter | |
{ | |
SerializationBinder binder; | |
StreamingContext context; | |
ISurrogateSelector surrogateSelector; | |
public CrappyIniFormatter() | |
{ | |
context = new StreamingContext(StreamingContextStates.All); | |
} | |
public object Deserialize(System.IO.Stream serializationStream) | |
{ | |
object obj = FormatterServices.GetUninitializedObject(typeof(IniFile)); | |
var members = FormatterServices.GetSerializableMembers(obj.GetType(), Context); | |
var sections = new List<Section>(); | |
Section section = null; | |
string key = null; | |
object value = null; | |
var sr = new StreamReader(serializationStream); | |
while (sr.Peek() >= 0) | |
{ | |
var line = sr.ReadLine(); | |
var sectionMatch = Regex.Match(line, @"^\[([^]]+)\]$"); | |
var stringEntryMatch = Regex.Match(line, @"^(.*?)=""(.*)""$"); | |
var floatEntryMatch = Regex.Match(line, @"^(.*?)=(.*)f$"); | |
if (sectionMatch.Success) | |
{ | |
if (section != null) | |
{ | |
sections.Add(section); | |
} | |
var title = sectionMatch.Groups[0].Value; | |
section = new Section { Entries = new Dictionary<string, object>(), Title = title }; | |
} | |
else if (stringEntryMatch.Success) | |
{ | |
key = stringEntryMatch.Groups[1].Value; | |
value = stringEntryMatch.Groups[2].Value; | |
} | |
else if (floatEntryMatch.Success) | |
{ | |
key = floatEntryMatch.Groups[1].Value; | |
value = float.Parse(floatEntryMatch.Groups[2].Value); | |
} | |
// any matches ... | |
if (key != null && value != null) | |
{ | |
section.Entries.Add(new KeyValuePair<string, object>(key, value)); | |
} | |
} | |
if (section != null) | |
{ | |
sections.Add(section); | |
} | |
object[] data = new object[1] { sections }; | |
return FormatterServices.PopulateObjectMembers(obj, members, data); | |
} | |
public void Serialize(System.IO.Stream serializationStream, object graph) | |
{ | |
var members = FormatterServices.GetSerializableMembers(graph.GetType(), Context); | |
object[] inifile = FormatterServices.GetObjectData(graph, members); | |
var sw = new StreamWriter(serializationStream); | |
if (inifile[0] is IEnumerable) | |
{ | |
foreach (object section in (inifile[0] as IEnumerable)) | |
{ | |
var title = section.GetType().GetField("Title").GetValue(section); | |
var entries = section.GetType().GetField("Entries").GetValue(section); | |
sw.WriteLine("[{0}]", title); | |
if (entries is IEnumerable) | |
{ | |
foreach (object entry in (entries as IEnumerable)) | |
{ | |
var key = entry.GetType().GetProperty("Key").GetValue(entry); | |
var value = entry.GetType().GetProperty("Value").GetValue(entry); | |
if (value is string) | |
{ | |
sw.WriteLine("{0}=\"{1}\"", key, value); | |
} | |
else if (value is float) | |
{ | |
sw.WriteLine("{0}={1}f", key, value.ToString()); | |
} | |
} | |
} | |
} | |
} | |
sw.Close(); | |
} | |
public ISurrogateSelector SurrogateSelector | |
{ | |
get { return surrogateSelector; } | |
set { surrogateSelector = value; } | |
} | |
public SerializationBinder Binder | |
{ | |
get { return binder; } | |
set { binder = value; } | |
} | |
public StreamingContext Context | |
{ | |
get { return context; } | |
set { context = value; } | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment