Structure de données permettant des recherches efficaces basées sur des balises


11

Je recherche une structure de données très efficace pour le stockage de données similaire à la suivante.

Étiquettes d'identification Order1 Order2 
--------------------------
1 1,2 1 1
2 2,5 2 3
3 1,7 4 7
4 6 3 0

J'ai besoin de pouvoir interroger cette structure de manière à ce qu'elle me donne une liste de tous les identifiants contenant une expression de balises - support ANDet ORet NOTopérations. Par exemple. ((1 ou 2) et non 7)

Je dois également pouvoir spécifier l'ordre des résultats (Order1 ou Order2) et pouvoir spécifier le nombre maximum de lignes renvoyées avec un décalage facultatif. La performance pour l'extraction des premiers 30 à 100 résultats est essentielle.

Enfin, j'ai besoin d'un moyen peu coûteux de rechercher des "relations de balise" par exemple, je veux savoir quelles balises "se rapportent" aux balises (1 OU 2) et à quelle fréquence. Signification des balises qui apparaissent dans le même ensemble que 1 OU 2 ... classées par fréquence.

Avez-vous une idée de quelle structure de données (ou ensemble de structures) serait très efficace pour ce type de travail?

(Je voudrais l'utiliser comme preuve de concept pour la refonte des pages balisées de la famille de sites SE)


1
Juste un commentaire (peut-être trivial). Pourquoi ne comptez-vous pas sur un système de gestion de bases de données relationnelles? Vous pouvez définir une table avec les paires <id, tag> et ajouter un index sur la colonne des balises. Vous pouvez ensuite utiliser des requêtes SQL standard pour extraire des données. Le SGBDR effectuera efficacement le «sale» travail d'optimisation des requêtes et de tri des sorties.
Marzio De Biasi

@Vor, les expressions sont incroyablement inefficaces à grande échelle, les auto-jointures deviennent des requêtes cauchemardesques.
Sam Saffron

@Sam: ok. Votre tâche est assez courante, j'ai donc pensé qu'un bon SGBDR (avec un outil d'exploration de données) pourrait faire le travail. Je laisse la parole à un expert en structure de données. :-)
Marzio De Biasi

Je crois qu'autoriser toutes les combinaisons de AND, OR, NOT va rendre difficile la création d'une structure de données qui ne répertorie pas tous les éléments (peut-être pourrait-elle être limitée à 3-CNF?). Si une telle limitation n'existe pas, alors peut-être parcourez simplement les enregistrements (dans l'ordre spécifié) jusqu'à ce que vous trouviez 30-100 qui répondent à vos exigences d'étiquette. Bien que, en général, je suis d'accord avec la suggestion de Vor d'utiliser une base de données pour faire le gros du travail pour vous.
bbejot

Pas un expert, mais je pense que si vous n'imposez pas de restrictions à la façon dont vous pouvez poser des questions sur les balises, cela va être difficile. Les limiter aux CNF (comme l'a suggéré bbejot) est une façon, une autre limite le nombre de balises différentes que la requête peut interroger sur un petit nombre (disons 6).
Kaveh

Réponses:


6

Ce n'est pas exactement la réponse d'une structure de données efficace, mais plutôt une élaboration sur les commentaires de @bbejot et @Kaveh donnant un argument de la main pour expliquer pourquoi, étant donné la question actuelle, nous ne devrions pas nous attendre à quelque chose qui fait beaucoup mieux que la recherche dans le base de données entière. L'argument est basé sur une réduction de SAT, l' hypothèse de temps exponentielle et beaucoup d'ondulations de la main.

nX|X|=nXj=1jXj=012nkkUNENORNOTn2n

Nous ne devons pas nous attendre à une recherche efficace sur la longueur de la requête (par réduction en SAT). Nous ne devrions pas non plus espérer mieux que de regarder tous les éléments de la base de données par l'hypothèse de temps exponentiel.

n1


Bonne observation. Chaque question a au plus 5 balises, donc une requête sur les balises équivaut à un 5-CNF.
Kaveh

Merci! oui, nous pouvons supposer davantage le 5-CNF ici, le comportement de marquage n'est pas aléatoire. En général, les gens marqueront les choses avec les balises les plus courantes, ce qui permettra quelques autres raccourcis.
Sam Saffron

1
@Kaveh, nous avons fini par rouler une structure en mémoire. Il existe quelques raccourcis non triviaux, le tri est un goulot d'étranglement, l'utilisation du tri en tas ou d'un tri rapide modifié vous permet de sélectionner efficacement les N premiers sans avoir besoin d'effectuer un tri complet. le pré-calcul des tris vous permet de sélectionner des pivots plus efficacement et d'éviter les tris lorsqu'un scan complet est nécessaire. le multithreading accélère les sélections. beaucoup de travail peut être reporté à l'arrière-plan avant que les utilisateurs n'interagissent avec les structures. étonnamment, nos structures en mémoire font en moyenne 0 ms pour une recherche dans l'ensemble de données de dépassement de pile.
Sam Saffron

@SamSaffron - Où est le post MSO détaillant cette fonctionnalité? Nous avons un rapport de bogue ici .
Kevin Vermeer

5

C'est une réponse assez simple, mais je pense efficace:

Map Tag ([Id],[Id])O(log(n))

Map Id (Set Tag)IdO(nlog(m))


J'ai tendance à convenir que certaines structures très simples comme une carte spoulée plusieurs fois peuvent être la meilleure façon d'aller ici. la mémoire est bon marché et maintenir plusieurs caches n'est pas trop difficile
Sam Saffron
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.