J'ai un modèle XYZ et j'ai besoin d'obtenir la valeur max pour les champs A, B et Expression X / Y pour un requérant donné.
Cela fonctionne magnifiquement pour les champs. Quelque chose comme: p> Cependant, je ne trouve pas un moyen de le faire pour les expressions. Essayer quelque chose comme: p> donne une erreur: p> essayer quelque chose comme: p> XYZ.all().extra(select={'z':'MAX(x/y)'})[0].z
4 Réponses :
Je pense que vous devez obtenir les valeurs maximales séparément puis diviser les deux champs p>
Cela n'a aucun sens. Même s'il renvoie la ligne avec la paire max x et Y, ce n'est pas nécessairement le max X / Y. Par exemple, la rangée max (x) / max (y) est 69/16 = 4, tandis que max (x / y) est 8/1 = 8
dans SQL, ce que vous voulez est en réalité donc dans django orm: p> la version p> XYZ.all().extra(select={'z':'MAX(x/y)'})[0].z
Droite, mais l'intention est d'obtenir la valeur max elle-même, comme le retour de xyz.all (). Agrégat (Max ('a')), pas l'instance le contenant. La version avec extra-sélection est la plus proche de celle-ci. Ne pas renvoyer la bonne instance est un effet secondaire déroutant, mais il renvoie la bonne valeur. Comme je l'ai dit dans le message d'ouverture, je suis au courant des solutions avec des commandes supplémentaires et des commandes, mais elles ne sont pas acceptables car elles nécessitent une sorte de table, pas une seule passe. Il n'a pas beaucoup de sens pour Django de soutenir Max agrégés avec des champs uniques mais pas des expressions.
@pjwerneck La raison de l'effet secondaire confus que vous avez appelé, est décrit dans le dernier paragraphe de ma réponse. Si vous voulez seulement une valeur maximale, xyz.object.extra (SELECT = {'Z': 'Max (x / y)'}) [0] .z code> suffit, il n'y a pas de commande_by. Ou même directement cursor.execute ('Sélectionnez max (x / y) de xyz') code>. Je suis d'accord avec vous que Django ne fournit pas d'agrégats avec des expressions, car il pourrait être considérablement plus difficile que de soutenir l'OMI sur le terrain unique.
Votre exemple qui utilise Il y a un extrait qui démontre l'agrégation avec f () code> Les objets doivent fonctionner correctement depuis Django 1.8: SUM () < / code> et f () code> objets dans Feuille de triche d'agrégation Django : p>
Bon à savoir. Merci!
Pour les versions inférieures à 1.8, vous pouvez obtenir la même chose de cette manière (non-documenté).
Book.objects.all().aggregate(price_per_page=Sum('price_per_page',
field='book_price/book_pages'))
Vous êtes peut-être intéressé de savoir que la possibilité d'utiliser
f () code> les objets des agrégats est Une partie de la prochaine version de Django 1.8 .