Kilka razy w przeszłości chciałem przechowywać dane w kodzie. Byłyby to dane, które rzadko się zmieniają i są wykorzystywane w miejscach, w których dostęp do bazy danych jest niemożliwy, praktyczny lub pożądany. Małym przykładem byłoby przechowywanie listy krajów. W tym celu możesz zrobić coś takiego:
public class Country
{
public string Code { get; set; }
public string EnglishName {get;set;}
}
public static class CountryHelper
{
public static List<Country> Countries = new List<Country>
{
new Country {Code = "AU", EnglishName = "Australia"},
...
new Country {Code = "SE", EnglishName = "Sweden"},
...
};
public static Country GetByCode(string code)
{
return Countries.Single(c => c.Code == code);
}
}
W przeszłości nie mogłem tego robić, ponieważ zestawy danych były stosunkowo małe, a obiekty dość proste. Teraz pracuję z czymś, co będzie miało bardziej złożone obiekty (5-10 właściwości każda, niektóre właściwości to słowniki) i łącznie około 200 obiektów.
Same dane zmieniają się bardzo rzadko, a kiedy się zmieniają, nie są nawet tak ważne. Tak więc włączenie go do następnej wersji jest w porządku.
Planuję użyć T4 lub ERB lub innego rozwiązania szablonowego, aby zmienić moje źródło danych w coś, co jest przechowywane statycznie w zestawie.
Wygląda na to, że moje opcje są
- Przechowuj dane w formacie XML. Skompiluj plik XML jako zasób zestawu. Załaduj dane w razie potrzeby, zapisz załadowane dane w Słowniku w celu zapewnienia wydajności wielokrotnego użytku.
- Wygeneruj jakiś statyczny obiekt lub obiekty, które zostaną zainicjowane podczas uruchamiania.
Jestem prawie pewien, że rozumiem wpływ opcji 1. na wydajność. Przynajmniej mam przeczucie, że nie miałaby ona znakomitej wydajności.
Jeśli chodzi o opcję 2, nie wiem, co robić. Nie wiem wystarczająco dużo o wewnętrznych elementach środowiska .NET, aby wiedzieć, jak najlepiej przechowywać te dane w kodzie C # i jak najlepiej je zainicjować. Rozglądałem się za pomocą odbłyśnika .NET, aby zobaczyć, jak System.Globalization.CultureInfo.GetCulture(name)działa, ponieważ w rzeczywistości jest to bardzo podobny przepływ pracy do tego, czego chcę. Niestety szlak ten zakończył się na extern, więc nie ma tam żadnych wskazówek. Czy inicjowanie właściwości statycznej za pomocą wszystkich danych, tak jak w moim przykładzie, jest właściwą drogą? A może lepiej byłoby tworzyć obiekty na żądanie, a następnie buforować je w ten sposób?
private static readonly Dictionary<string, Country> Cache = new Dictionary<string,Country>();
public static Country GetByCode(string code)
{
if (!Cache.ContainsKey(code))
return Cache[code];
return (Cache[code] = CreateCountry(code));
}
internal static Country CreateCountry(string code)
{
if (code == "AU")
return new Country {Code = "AU", EnglishName = "Australia"};
...
if (code == "SE")
return new Country {Code = "SE", EnglishName = "Sweden"};
...
throw new CountryNotFoundException();
}
Zaletą tworzenia ich naraz w statycznym elemencie jest to, że możesz użyć LINQ lub cokolwiek innego, aby spojrzeć na wszystkie obiekty i zapytać je, jeśli chcesz. Chociaż podejrzewam, że robienie tego ma negatywny wpływ na wydajność uruchamiania. Mam nadzieję, że ktoś ma z tym doświadczenie i może podzielić się swoimi opiniami!