11
votes

C # Dictionnaire: accès plus rapide mais moins de l'empreinte mémoire

Je veux des conseils sur la meilleure façon de stocker et d'accéder à une empreinte de mémoire minimale et de performances d'accès maximales.

par exemple. Pour chaque véhicule, je veux stocker le modèle et le nom. p>

J'ai quelques pensées ci-dessous: P>

Option 1: P>

Dictionary<string, List<string>> values1 = new Dictionary<string, List<string>>();
List<string> list1 = new List<string>();
list1.Add("2001:Jetta S");
list1.Add("2002:Jetta SE");
list1.Add("2002:Jetta LE");
values1.Add("VolksWagen", list1);


6 commentaires

"Avec une empreinte minimale en mémoire et des performances d'accès maximales." - ce sont généralement des contraintes opposées (temps contre l'espace)


L'option 1 ne vient pas de lancer une exception pour des touches en double?


À quelle fréquence ces listes sont-elles mises à jour?


Personnellement, j'aime le code simple et lisible, à moins que le code ne soit trop lent pour courir que je suis obligé de faire face à la question de la performance. Je pense que tout le monde a vu la liste > serait un peu bizarre.


Suggera de créer une structure pour l'encapsulation d'une année et la performance de fabrication sera identique à celle de KeyValuePair, mais que le code serait beaucoup plus lisible.


@Dannychen Je crois aussi que le KVP est inutile de commencer, et le tuple serait plus rapide.


4 Réponses :


21
votes

tritedList est une liste à plat (sans augmenter énorme de l'empreinte mémoire), qui utilise la recherche binaire d'accès - donc o (log (n)) < / Code> - Donc pas aussi vite que Dictionnaire au O (1) - mais beaucoup mieux qu'une liste (ou une autre recherche linéaire) à o (n) .

Si vous voulez l'accès le plus rapide , vous devez utiliser une mémoire supplémentaire pour une table HASH.

comme une note latérale, TritedList permet également un accès efficace par Int Index , qui est difficile pour Soyeddicary , et pratiquement sans signification pour Dictionnaire .

Évidemment dans votre scénario, vous devrez peut-être combiner tritedlist <,> avec une nidification ou une clé composite - mais imo qui va être votre meilleur itinéraire pour obtenir un équilibre de la mémoire et des accessoires-performance. Vous pouvez utiliser une clé composite dédiée, c'est-à-dire un IUMUMUTABLE struct avec les membres de la clé composite, le remplacement gethascode () et est égal à , implémentation Iequatable , et pour le tri: implémentation icomparable et icomparable . .


0 commentaires

3
votes

Vous ne devez pas choisir votre structure de données principalement par la mémoire "Empreinte", mais par motif d'accès: Quelles sont les recherches les plus fréquentes que vous souhaitez faire, quelle fréquence la structure sera mise à jour et ainsi de suite.

Si vous voulez remplir la structure une fois, recherchez les voitures par année de fabrication et de construction, la première approche semble plus raisonnable (et lisible / compréhensible).

BTW, étant donné que plusieurs modèles peuvent être libérés en un an, vous devez probablement utiliser un dictionnaire Dictionary >> . Et si c'est vraiment des années que vous souhaitez stocker, vous ne devez pas utiliser de chaînes comme clés, mais int16 à la place.


0 commentaires

1
votes

Lorsque vous parlez d'accès dans les structures de données, il est important de comprendre la différence entre Lire Strong> Accès et écrire strong> Accès. Quant au dictionnaire, vous obtiendrez o (1) code> accès à la valeur code> par clé code> heure, mais O (log (nd) ) CODE> Écrivez du temps, si je ne me trompe pas. En utilisant des listes simples, il est toujours O (1) code> à ajouter, mais c'est o (n) code> pour accéder aux données. En ce qui concerne l'empreinte mémoire, il est à peu près le même: O (n) code> dans le pire des cas.

Combien de valeurs avez-vous besoin de stocker / d'accès? Selon vos échantillons de code, P>

option 1: est inapproprié: p>

list.Add("2002", "Jetta SE");
list.Add("2002", "Jetta LE");


3 commentaires

Le O (1) pour ajouter suppose que vous ajoutez à la fin ; Insérer peut être coûteux pour les listes de tableau (beaucoup mieux pour les listes liées, évidemment)


Re l'empreinte de l'opération - Si l'objectif de l'OP est de réduire une empreinte mémoire, un appartement O (n) peut être vrai mais inutile; Avec des implémentations A et B, A pourrait prendre 5000 fois plus d'espace que B, et toujours les deux O (n)


@Marc, j'ai édité mon message, ajouté "dans le pire des cas". En ce qui concerne l'écriture de temps, l'insertion ne doit pas nécessairement être coûteuse si vous gardez le dernier index, puis utilisez-le simplement. Bien sûr, nous devrions discuter de la réaffectation ici, mais peu importe dans un contexte de la question :)



2
votes

Vous pouvez utiliser un dictionnaire avec nomvaluecollection : xxx

ou avec des initialisateurs de collecte: xxx < / Pré>

Bien que je ne sois pas expert sur la mémoire de mémoire, IMHO Cela vous fournira le meilleur modèle d'accès dans ce scénario particulier.


0 commentaires