3 votes

Une base de données graphique ou relationnelle est préférable pour cette structure arborescente ?

Je suis novice en matière de bases de données graphiques et j'ai besoin d'une recommandation pour ce scénario. J'ai des personnes qui aiment les catégories (seulement les feuilles de l'arbre), les autres nœuds (parents) ne reçoivent pas de "like". Ensuite, je calcule un score pour toutes les connexions d'un utilisateur spécifique à d'autres utilisateurs. Voici un exemple graphique :

enter image description here

J'ai essayé avec neo4j et je n'ai aucun problème (très petit ensemble de données), mais j'ai peur des performances avec beaucoup d'utilisateurs. J'ai testé avec la requête suivante :

MATCH (n:Person)-[:LIKES*]->()-[r:SUB*0..4]-()<-[:LIKES*]-(m:Person)
WHERE n.name='Gabriel' and n<>m
WITH n.name as user, m.name as connection, 1.0/(length(r)+1)*count(r) as score
RETURN user, connection, sum(score)

J'ai également pensé à le faire dans une base de données relationnelle, en sauvegardant 3 champs pour les catégories (cat1, cat2, cat3) et en effectuant ensuite 3 jointures automatiques, en recherchant les correspondances dans les différents niveaux de catégories. Quelque chose comme ça (en commençant par l'utilisateur 1 et en essayant de trouver des correspondances avec les autres) :

select l2.user_id, sum(
case 
    when (l1.cat2 = l2.cat2 and l1.cat3 = l2.cat3) then 1
    when (l1.cat2 = l2.cat2) then 0.25 
    else 0.05 
end)
from likes l1
inner join likes l2 on l1.cat1 = l2.cat1 and l2.user_id <> 1
where l1.user_id = 1 
group by l2.user_id

mais j'ai aussi lu que vous devriez éviter de faire des auto-joints.

Je précise que je recherche les performances en lecture, l'écriture n'a pas d'importance. Mon objectif est qu'il fonctionne bien avec 1 million d'utilisateurs avec 10 likes chacun. Je suis à l'écoute de tout type d'opinion, merci !

1voto

FoxArc Points 79

TLDR ; IMO une base de données relationnelle serait mieux puisque vous cherchez à savoir comment une chose est liée à une autre, c'est-à-dire combien de likes (des équipes) une personne a. Vous pouvez facilement mettre à jour les métadonnées sur les utilisateurs, les équipes ou les sports sans craindre de perturber vos requêtes analytiques. De plus, vous pouvez facilement ajouter des types de sports tels que l'université, le lycée, etc. sans craindre que votre configuration précédente ne soit perturbée.

MAIS, je dois avouer que je n'ai jamais utilisé de base de données graphique auparavant :)


Une base de données de relations pourrait ressembler à quelque chose comme ceci :

J'aime appeler ces tables d'information car elles ne donnent que les informations, certains les appellent aussi tables de référence, sur un élément spécifique : Sport (Sport_ID, Sport_Name, [etc]...) Noms de sport comme Football, Basketball, etc... Exemple de vue :

 Sport_ID  Sport_Name  ... 

        1  Football    ... 
        2  Basketball  ... 
     ...   ...         ... 

Team (Team_ID, Team_Name, Home_State, [etc]...) -- Les équipes seraient toutes les équipes, quel que soit le type de sport dans lequel elles se trouvent. Exemple de vue :

 Team_ID   Team_Name   ... 

       1  Boca Junior  ... 
       2  River Plate  ... 
       3  Spurs        ... 
     ...  ...          ... 

Utilisateur (User_ID, User_First_Name, [etc]...) -- Toutes les informations spécifiques à l'utilisateur vont ici. Exemple de vue :

 User_ID  User_First_Name  ... 

       1  Mario            ... 
       2  Gabriel          ... 
       3  Juana            ... 
       4  Raul             ... 
     ...  ...              ... 

Ensuite, vous créerez les tables de relation pour établir les liens entre les sports, les équipes et les utilisateurs.

Sports_Team (Sport_ID, Team_ID) -- Il s'agit d'indiquer quelle équipe a joué dans quel sport. Exemple de vue :

 Sport_ID  Team_ID  ... 

        1        1  ... 
        1        2  ... 
        2        3  ... 
      ...      ...  ... 

Team_User_Likes (Team_ID, User_ID) -- Ici vous montrerez quelle personne aime quelle équipe a joué quel sport. Exemple de vue :

 Team_ID  User_ID  ... 

       1        1  ... 
       2        2  ... 
       2        3  ... 
       3        3  ... 
     ...      ...  ... 

Maintenant, tout ce que vous avez à faire est d'obtenir un score sur le nombre d'équipes qu'un utilisateur aime :

SELECT tul.User_ID
     , COUNT(tul.Team_ID) AS Likes
  FROM team_user_likes tul
 GROUP
    BY tul.User_ID

Et si vous voulez les métadonnées des utilisateurs, comme leurs noms, vous pouvez lancer cette requête dans un CTE et ensuite utiliser la table des utilisateurs pour joindre la table du CTE.

Cela peut sembler compliqué, mais il sera plus facile de modifier/mettre à jour les informations sur les utilisateurs, les équipes et les sports. Vous serez en mesure d'effectuer des analyses intéressantes, comme le nombre d'utilisateurs qui aiment/préfèrent un sport plutôt qu'un autre en utilisant les données de préférence sans avoir à vous soucier d'affecter les tables relationnelles, ou l'équipe de chaque sport qui est la favorite de la majorité.

De plus, cela devrait pouvoir évoluer facilement, en fonction de la base de données relationnelle que vous utilisez. Et si vous voulez commencer à ajouter des sports de lycée, d'université, etc., vous pouvez simplement ajouter une table sport_type puis créer une table de relation sport_sport_type pour faire le lien entre les sports professionnels et les autres. Viola, vous pouvez alors faire des analyses par type de sport sans vous soucier de la façon dont cela affecte votre configuration précédente.

Je préfère les bases de données relationnelles car elles semblent garder les choses plus ordonnées. Tout ceci étant dit, je n'ai jamais utilisé de base de données de graphes. Mais étant donné que vous voyez comment une chose est liée à une autre, c'est-à-dire combien d'équipes une personne aime, je pense que vous devriez opter pour une base de données relationnelle.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X