2009-01-12 5 views
1

Ayende a un blog post détaillant comment combattre le problème "n + 1" dans nHibernate. En substance, le problème est le suivant:Comment éviter le problème n + 1 avec SubSonic?

Supposons que vous avez deux tables, "BlogPosts" et "Commentaires" avec une relation un-à-plusieurs entre eux (par exemple, chaque BlogPost peut avoir plusieurs commentaires). Maintenant, disons que vous voulez exécuter la imbriquée boucle suivante:

foreach (BlogPost post in blogposts) 
{ 
    foreach (Comment comment in post.Comments) 
    { 
     // Do something 
    } 
} 

D'après ce que je comprends, les classes qui SubSonic génèrent sont lazyload par défaut (je ne veux pas le désactiver complètement parce qu'il est utile la plupart des circonstances, mais pas celle-ci). Cela signifie qu'à chaque fois que la boucle interne est exécutée (c'est-à-dire lorsque l'on accède à post.Comments), une requête séparée doit être envoyée à la base de données pour récupérer les commentaires. Donc, si vous avez 80 billets de blog, c'est 1 requête pour obtenir la liste des articles de blog, puis 80 requêtes pour obtenir les commentaires pour chacun d'entre eux. Si les commentaires étaient chargés, cependant, cela serait réduit à 1 requête.

Y at-il un moyen de lutter contre ce problème dans SubSonic actuellement?

Répondre

2

À moins que vous ne créiez une requête pour sélectionner un commentaire à partir des ID de message, je ne pense pas qu'il existe un moyen de le combattre. Cela vous ramènerait à deux. Une requête pour sélectionner les ID de poste que vous souhaitez, puis une autre pour obtenir tous les commentaires pour cette liste d'ID de publication.

+0

Hmm. C'est malheureux. Alors qu'en est-il du cas où vous avez un lien GridView lié à un BlogPostCollection et que vous voulez afficher, disons, le nombre de commentaires pour ce BlogPost? –

1

Je pense que ce que vous devriez faire est de créer une méthode de classe partielle qui obtiendra tous les commentaires. Pas si propre mais ça devrait marcher.

0

J'utilise aussi des classes partielles et des classes de table liées à la charge comme ceci:

Partial Public Class Book 

    Private _Author as Database.Author 
    Property Author() as Database.Author 
     Get 
     If _Author is nothing then 
      ' Load the author class here. 
     End if 
     return _Author 
     End get 
     Set 
     '.... 
     End Set 
    End Property 

End Class 
Questions connexes