it-swarm.com.de

Erstellen eines konstanten Wörterbuchs in C #

Was ist der effizienteste Weg, um eine konstante (ändert sich nie zur Laufzeit) Zuordnung von strings zu ints zu erstellen?

Ich habe versucht, ein const Dictionary zu verwenden, aber das hat nicht geklappt.

Ich könnte einen nveränderlichen Wrapper mit entsprechender Semantik implementieren, aber das scheint immer noch nicht ganz richtig zu sein.


Für diejenigen, die gefragt haben, implementiere ich IDataErrorInfo in eine generierte Klasse und suche nach einer Möglichkeit, den columnName-Lookup in mein Array von Deskriptoren aufzunehmen.

Ich wusste nicht (Tippfehler beim Testen! D'oh!), Dass der Schalter Zeichenfolgen akzeptiert, also werde ich diese verwenden. Vielen Dank!

113
David Schmitt

Das Erstellen eines während der Kompilierung generierten Konstantenwörterbuchs in C # ist keine einfache Aufgabe. Tatsächlich erreicht keine der Antworten hier das wirklich.

Es gibt jedoch eine Lösung, die Ihren Anforderungen entspricht, wenn auch nicht unbedingt eine gute. Denken Sie daran, dass Switch-Case-Tabellen gemäß der C # -Spezifikation zu konstanten Hash-Jump-Tabellen kompiliert werden. Das heißt, sie sind konstante Wörterbücher und keine Reihe von if-else-Anweisungen. Betrachten Sie also eine switch-case-Anweisung wie diese:

switch (myString)
{
   case "cat": return 0;
   case "dog": return 1;
   case "elephant": return 3;
}

Genau das wollen Sie. Und ja, ich weiß, es ist hässlich.

167
Tamas Czinege

Im aktuellen Rahmen gibt es nur wenige unveränderliche Sammlungen. Ich kann mir eine relativ schmerzfreie Option in .NET 3.5 vorstellen:

Benutze Enumerable.ToLookup() - das Lookup<,> Klasse ist unveränderlich (aber am rhs mehrwertig); Sie können dies von einem Dictionary<,> ziemlich einfach:

    Dictionary<string, int> ids = new Dictionary<string, int> {
      {"abc",1}, {"def",2}, {"ghi",3}
    };
    ILookup<string, int> lookup = ids.ToLookup(x => x.Key, x => x.Value);
    int i = lookup["def"].Single();
36
Marc Gravell
enum Constants
{
    Abc = 1,
    Def = 2,
    Ghi = 3
}

...

int i = (int)Enum.Parse(typeof(Constants), "Def");
14
Richard Poole

Dies ist die nächste Sache, die Sie zu einem "CONST Dictionary" bekommen können:

public static int GetValueByName(string name)
{
    switch (name)
    {
        case "bob": return 1;
        case "billy": return 2;
        default: return -1;
    }
}

Der Compiler ist intelligent genug, um den Code so sauber wie möglich zu erstellen.

10
Timothy Khouri

Wenn ich mehr als 4.5 Framework verwende, verwende ich ReadOnlyDictionary (auch ReadOnly Collection für Listen), um schreibgeschützte Zuordnungen/Konstanten zu erstellen. Es wird folgendermaßen implementiert.

static class SomeClass
{
    static readonly ReadOnlyDictionary<string,int> SOME_MAPPING 
        = new ReadOnlyDictionary<string,int>(
            new Dictionary<string,int>()
            {
                { "One", 1 },
                { "Two", 2 }
            }
        )
}        
3
Kram

Verwenden Sie Namespaces oder Klassen, um Ihre Werte zu verschachteln. Es mag unvollkommen sein, aber es ist sehr sauber.

public static class ParentClass
{
    // here is the "dictionary" class
    public static class FooDictionary
    {
        public const string Key1 = "somevalue";
        public const string Foobar = "fubar";
    }
}

Jetzt können Sie auf .ParentClass.FooDictionary.Key1 usw. zugreifen.

2
Joshua

Es scheint keine unveränderliche Standardschnittstelle für Wörterbücher zu geben, so dass das Erstellen eines Wrappers leider die einzig sinnvolle Option ist.

Edit: Marc Gravell hat das ILookup gefunden, das ich verpasst habe - so können Sie zumindest vermeiden, einen neuen Wrapper zu erstellen, obwohl Sie das Dictionary noch mit .ToLookup () transformieren müssen.

Wenn diese Anforderung auf ein bestimmtes Szenario beschränkt ist, ist eine stärker auf Geschäftslogik ausgerichtete Schnittstelle möglicherweise besser für Sie geeignet:

interface IActiveUserCountProvider
{
    int GetMaxForServer(string serverName);
}
1
Sander

Ich bin nicht sicher, warum niemand dies erwähnte, aber in C # verwende ich für Dinge, die ich const nicht zuweisen kann, statische schreibgeschützte Eigenschaften.

Beispiel:

public static readonly Dictionary<string, string[]> NewDictionary = new Dictionary<string, string[]>()
        {
            { "Reference1", Array1 },
            { "Reference2", Array2 },
            { "Reference3", Array3 },
            { "Reference4", Array4 },
            { "Reference5", Array5 }
        };
0
Suleman