Aller au contenu

[RESOLU]Afficher le + gd ID de plusieurs sous_id


Bitibulleur

Messages recommandés

Bonjour à toute la communité Impacticienne.

Après pas mal de temps, je reviens vers vous pour que vous puissiez m'éclairer de vos lumières Ô combien éblouissantes :byebye:

=>edit du sujet : Afficher le plus grand ID de plusieurs sous_id

Je tiens à faire savoir que je ne suis pas totalement Newbie mais pas expert pour un rond non plus => je n'ai que quelques notion de requète Mysql et PHP

J'ose espérer que le titre et sa description sont assez clairs mais je m'explique.

Je suis donc sous php, avec une bdd mysql.

Pour simplifier disons que j'ai une table fruit avec comme champ

-id_fruit autoincrement

-id_typefruit (smallint) (=> renvoit à une table typefruit par une jointure pour avoir le nom)

-id_fruitpoid (smallint)

-id_fruitdate(date)

il est possible d'avoir les enregistrements :

id_fruit | id_typefruit | id_fruitpoid | id_fruitdate |

-----------------------------------------------

1 | 1 | 312 | 2010/02/01 |

2 | 1 | 152 | 2010/02/21 |

3 | 1 | 317 | 2010/02/22 |

4 | 2 | 87 | 2010/02/17 |

5 | 2 | 367 | 2010/02/20 |

6 | 3 | 287 | 2010/02/03 |

7 | 1 | 256 | 2010/02/18 |

8 | 2 | 213 | 2010/02/18 |

9 | 3 | 152 | 2010/02/06 |

10 | 2 | 717 | 2010/02/16 |

Je cherche donc à afficher le poid le plus grand de chaqu'un de mes fruits... sans tenir compte de la date (qui correpond à un date d'achat, pas de saisie...) mais ordonné par type de fruit

Cela devrai me donner :

le 22/02/2010 achat de 317 Kg de pommes (=> id_fruit=3 | id_typefruit=1 | id_poidfruit=317)

le 16/02/2010 achat de 717 Kg de fraises (=> id_fruit=10 | id_typefruit=2 | id_poidfruit=717)

le 03/02/2010 achat de 287 kg de bananes (=> id_fruit=6 | id_typefruit=3 | id_poidfruit=287)

J'avoue que je tourne en rond :D depuis quelques jours et vos idées seront les bienvenues... :cartonrouge:

Par avance merci .....

Lien vers le commentaire
Partager sur d’autres sites

Connaissez-vous le nombre de types de fruits, ou c'est variable ?

Si c'est variable, il faudrait faire une requête par type, et utiliser la commande LIMIT pour limiter à un seul résultat...

Je ne suis pas du tour expert en SQL, donc si quelqu'un a une autre idée :cartonrouge:

... C'est variable ...... il par contre il n'y a "que" 12 type de fruits au maximum, mais un nombre très varible de "sous fruit" si je puis dire ... (pommes rouges, pomme vertes, pome jaunes, ...) c'est ce qui complique un peut la vie .. (ce serait pas drôle sinon ....)

... en fait afficher le tout ne me pose aucun problème, mais afficher le plus grand poid, oui (un peu comme vouloir affiche le record d'achat de poid).

=> L'histoire de fruits n'est là que pour exemple.

Sinon c'est un pour un site d'assoc' sportive, je voudrais afficher le dernier résultat de chaque équipe, qui joue chacune à des dates différentes (=> journées différente) avec des saisie faites à des moment 'M' différents. Sachant que pour des raisons X ou Y les journée peuvent être inversée (jounée en retard par ex.....)

=> bref pas simple tout ça .... :D

Lien vers le commentaire
Partager sur d’autres sites

Dans ce cas, je crois qu'une requête par type va être nécessaire ;)

Ok.

Le prob, c'est que, fatigue et ras le bol aidant, je ne sais plus (pas )trop comment "imbriquer ces requetes.

Il faudrait :

1-requete pour vérifier si le id_fruittype existe

2-récupérer le max(id_fruitpoid) de chaque résultat de la requete précédente...

Mais je ne sais plus comment ... boule while imbriquées ?

Honnètement je sêche.... ;)

Lien vers le commentaire
Partager sur d’autres sites

A la limite, une seule requête par type est nécessaire, avec le ORDER BY qui va bien, le LIMIT qui va bien pour limiter à un seul résultat, et enfin via PHP / MySQL compter les résultats pour qu'il y en ait au moins 1 (si 0, c'est que ça ne marche pas, ou rien à lire en stock)

S'il y a besoin, je donnerais un exemple, en espérant qu'il corresponde bien ;)

Lien vers le commentaire
Partager sur d’autres sites

Je pense que c'est possible avec une bonne requête bien tordue mais je n'ai pas pu trouver la solution rapidement...

En attendant, tu peux "tricher" de la manière suivante :

- Récupérer tous les types de fruits

SELECT id_typefruit FROM fruits GROUP BY id_typefruit

- Ensuite pour chaque type de fruit récupéré, demander le plus lourd :

SELECT * FROM fruits WHERE id_typefruit=? ORDER BY poids LIMIT 1

Lien vers le commentaire
Partager sur d’autres sites

Je pense que c'est possible avec une bonne requête bien tordue mais je n'ai pas pu trouver la solution rapidement...

En attendant, tu peux "tricher" de la manière suivante :

- Récupérer tous les types de fruits

SELECT id_typefruit FROM fruits GROUP BY id_typefruit

- Ensuite pour chaque type de fruit récupéré, demander le plus lourd :

SELECT * FROM fruits WHERE id_typefruit=? ORDER BY poids LIMIT 1

Merci de ta réponse et de ton aide ô combien précieuse !

En m'inspirant de celles-ci, j'ai adapté mes requetes et arrive à un résultat, somme toute, correct.

Pour info, si celà peut aider certain(e)s :

$req1=mysql_query("SELECT id_typefruit FROM fruit GROUP BY idtypefruit") or die(moysql_error());
while($res1=mysql_fetch_array)) 
//=> me donne la liste des types de fruits dans un array (ou tableau pour le ultra-noninitié)
{
$req2=mysql_query("SELECT * FROM fruit WHERE id_typefruit='".$res1['id_typefruit'].'" ORDER BY id_fruitpoid LIMIT 1") or die(mysql_error());
while($res2=mysql_fetch_array($req2)
{
echo "ce dont j'ai besoin";
}
}

=> sans oublier certaines jointures avant le WHERE clause ... et un 'petit 'HAVING' clause avant le 'ORDER' pour rajouter une "condition"

Merci à vous 'Amour' (celà fait "bizzard" de dire amour comme ça !!! ;) ), mais tu en as été un !!! ;) et 'Shtong' qui m'a définitivement mis sur la voie !

Si vous avez des remarque sur ce code ... dites moi ....!

Merci encore

Je considère le sujet comme résolu .. (mais comment fait-on pour le marquer comme "résolu" ?)

Lien vers le commentaire
Partager sur d’autres sites

Non ce n'est pas résolu, avec cette solution tu fais N+1 requêtes alors que tu peux le faire en une seule !!!

SELECT
    *
FROM (
    SELECT
        id_fruit,      id_typefruit,
        id_poidsfruit, id_fruitdate
    FROM
        fruits
    ORDER BY
        id_poidsfruit DESC
    ) AS t
GROUP BY
    id_typefruit

De plus il y a plusieurs choses qui attirent mon attention sur la description de ta table, le type de ton champ id_poidsfruit devrait être à virgule flottante (un FLOAT devrait faire l'affaire dans ce cas) et non un INTEGER. De plus tes champs sont mal nommés, pourquoi sont ils tous préfixés "id" alors que seule ta clé primaire et ta clé étrangère sont des identifiants ? pourquoi "id_fruitdate", "id_datefruit" ne serait il pas plus cohérent avec tes autres champ ?

Dans l'idéal tu devrait avoir quelque chose de ce genre :

  frt_fruitId    INTEGER AUTOINCREMENT <pk>
 frt_typeId     INTEGER <fk>
 frt_fruitPoids FLOAT   NOT NULL
 frt_fruitAchat DATE    NOT NULL

Je suis peut être un peu pinailleur, mais quand to commencera à bosser sur de vrais modèles de données complexes, tu te rendra vite compte que des conventions de nommage strictes sont essentielles.

Lien vers le commentaire
Partager sur d’autres sites

Merci 'Yangzebul' te t'être penché sur ce sujet bien qu'il est été marqué 'resolu' ....

=> je corrige de ce pas .......

Je te rejoins , malgré ma 'novicitude' en matière de base de données, quant au fait qu'il faille se conformer au convention de nommage (que je ne maitrise pas... -sic-), mais pour l'exemple , j'ai voulu simplifier sans chercher plus loin.

Si je rentre dans les détails et si je parle de mon cas précis (qui à mon sens n'est pas toujours utile pour tous ceux et toutes celles qui ont besoin d'aide), je cherche à afficher les derniers résultats sportifs de l'association dont je m'occupe. (côté web).

J'ai donc un base MySQL 'calendrier' avec les champs suivant :

- Idcal (autoincrement)

- Idequ (smallint-2)(=> qui me sert, à l'aide d'une jointure, à récupérer le nom de mon équipe ...)

- num(smallin-2) (=> le numéro e la journée : 25 maxi à l'heure actuelle, mais n'a pas de limite officielle)

- match (smallint-3)(=> le numéro de match entre 100 et 500 à l'heure actuelle, mais n'a pas de limite officielle également)

- jour (smallint-1) (=> je récupère le jour par une jointure => une table a été faite pour ça pour des raisons précises mais longues à expliquer)

- date(date)

+ 5 autres champs qui me permettent pour récupérer le nom de l'adversaire (jointure), m'indiquer le lieu (domicile/déplacement), l'heure du match, les points encaissés, les points marqués......

Normalement, lors de la création des calendriers, tout devrait être ordonné (les 22 premeirs enregistrement concernent l'équipe 1, les 12 suivant la 2, les 17 autre la 3 etc .......), mais un oublie pourrait être fait, j'ai donc prévu de pouvoir rajouter une journée....

Comme tous résultats sportifs certaines jounée peuvent être décalées l'équipe 1 jouant num1 - num2- num4 puis num3 (inversion 3 et 4) pendant que equipe 2 ne joue pas puis num1 - num2 ...

La chose n'est somme toute, pas si simple.

Il faudrait que je récupère pour chaque équipe le dernier résultat de la dernière journée jouée en fonction aussi de la date ..... (num4 se jouant avant num3 qu'il faudra que j'affiche lorsque celle ci aurra lieu...)

Pour en revenir à ton code 'Yangzebul' , j'avoue mon ignorance quant aux requetes imbriquées, et le 'AS' ....

Désolé, mais j'aime comprendre ce que je fais et recopier "bêtement" n'est pas très interressant. Parfois un code bien expliqué est beaucoup plus instructif ....

si cela t'intéresse, je peux toujours poster le code tel qu'il est, fonctionnel, même s'il me manque la prise en compte de l'inversion des journée.

Bon sang, que j'aime pas les message à rallonge !!!!!!!!!! :youhou::francais:

PS : le code fonctionne => adapté à la réalité, mais peut-on rajouter une selection en fonction de la date de la journée ? (tjs si j3 se joue après j4 ..)

Lien vers le commentaire
Partager sur d’autres sites

Le principe est très simple : c'est une requête imbriquée.

Au lieu de faire une requête sur une table tu fais ta requête sur le résultat d'une autre requête.

Le AS sert à définir un alias pour un champ ou une table, dans ce cas précis il ne sert à rien, mais il est requis par mysql.

La première requête retourne tout les enregistrements triés par poids, et la seconde groupe par type de fruit : on a donc seulement le premier enregistrement de chaque type de fruit, et comme on fait ce regroupement sur un résultat déjà trié par poids, on obtient ce que tu veux.

Après si tu veux extraire un certain jour, tu peux rajouter une clause where dans la requête interne.

Le plus simple pour bien comprendre c'est que tu prenne le requête interne, et que tu l'exécute.

PS : cela ne marche pas sur les tables myisam, mais de toute façon quasiment rien ne marche sur les tables myisam.

Lien vers le commentaire
Partager sur d’autres sites

Le principe est très simple : c'est une requête imbriquée.

Au lieu de faire une requête sur une table tu fais ta requête sur le résultat d'une autre requête.

Le AS sert à définir un alias pour un champ ou une table, dans ce cas précis il ne sert à rien, mais il est requis par mysql.

Merci de ton éclairage. Finalement en relisant ton code et le mien, il y avait trop de similitude pour ne pas "comprendre" et concernant le AS, comme je ne voyais pas son "utilité" mais MySQL le voulait quand même présent ......

La première requête retourne tout les enregistrements triés par poids, et la seconde groupe par type de fruit : on a donc seulement le premier enregistrement de chaque type de fruit, et comme on fait ce regroupement sur un résultat déjà trié par poids, on obtient ce que tu veux.

=> l'imbrication des requetes .... 1 pour le prix de 2 .... et c'est plus économique ..!!! Si seulement c'était tout aussi vrai dans le commerce !! :youhou:

Après si tu veux extraire un certain jour, tu peux rajouter une clause where dans la requête interne.

Le problème est que j'ai déja 2 clause WHERE (pour>0 || contre>0) et je n'arrive pas en a mettre une autre (&& date=MAX(date) :francais:

Le plus simple pour bien comprendre c'est que tu prenne le requête interne, et que tu l'exécute.
=> j'avais vu.... :ouioui: et si j'ai bien compris, on exécute la requete la plus "enfermée", puis on remonte ....
PS : cela ne marche pas sur les tables myisam, mais de toute façon quasiment rien ne marche sur les tables myisam.
ah ..? désole mais je sais pas ce que c'est ... (MySQL me suffit à mon niveau => bénévole curieux) :zarb:

Merci te tes infos en tout cas .... Si j'avais connu ces "inbrication" de requete (tout comme le fut passé un temps les jointures) certaines requetes aurais été bien plus simple .. Si j'ai le temps (un jour) j'essaierais de les "clarifier"...

Si tu as encore des infos, je suis tout "oeil".........

Merci encore

Lien vers le commentaire
Partager sur d’autres sites

"ah ..? désole mais je sais pas ce que c'est ... (MySQL me suffit à mon niveau => bénévole curieux)"

myisam c'est un ancien format de table, mysql à la particularité de pouvoir gérer plusieurs format de tables dans une même base.

Le format de préférence est maintenant innoDB qui permet de vraies jointures avec des contraintes d'intégrité.

En fait maintenant que j'y réfléchit je ne suis pas très sûr que les limitations sur les requêtes imbriquées proviennent de la version de mysql  plutot que du format de table (à moins que ce soit les deux). Sous mysql 3 ce n'était pas possible, mais de toute facon OSEF, si ça marche chez toi, tant mieux.

Bonne nuit et bon courage pour ton appli.  :francais:

Lien vers le commentaire
Partager sur d’autres sites

myisam c'est un ancien format de table, mysql à la particularité de pouvoir gérer plusieurs format de tables dans une même base.

Le format de préférence est maintenant innoDB qui permet de vraies jointures avec des contraintes d'intégrité.

En fait maintenant que j'y réfléchit je ne suis pas très sûr que les limitations sur les requêtes imbriquées proviennent de la version de mysql  plutot que du format de table (à moins que ce soit les deux). Sous mysql 3 ce n'était pas possible, mais de toute facon OSEF, si ça marche chez toi, tant mieux.

Bonne nuit et bon courage pour ton appli.  :francais:

J'avoue utiliser (sans avoir bien réfléchit à la question, car tout marche) du MyISAM et tout va bien, peut-être que certaines limitations ont sauté ?

Lien vers le commentaire
Partager sur d’autres sites

 

J'avoue utiliser (sans avoir bien réfléchit à la question, car tout marche) du MyISAM et tout va bien, peut-être que certaines limitations ont sauté ?

La limitation doit surement venir de la version de mySQL dans ce cas.

Par contre ce dont je suis sur c'est que myisam ne supporte pas les contraintes d'intégrité, tu ne peux donc pas faire de vraies jointures avec ce format de table.

http://dev.mysql.com/doc/refman/5.5/en/ans...reign-keys.html

"At a later stage, foreign key constraints will be implemented for MyISAM tables as well." << ne pas se fier à ça, cela fait depuis mysql3 que c'est annoncé, en réalité myisam n'est quasiment plus supporté.

Le mieux est de faire si possible toutes ses tables en innodb.

Lien vers le commentaire
Partager sur d’autres sites

Juste pour dire "merci".

Concernant les table MyISAM ou MySQL, je ne connais pas les différences, ne connaissant pas la première...

Concenant le code, l'imbrication fonctionne à merveille, et avec un peu de repos, je fait un tri par date, c'est plus simple ...

Merci encore.

=> je considère comme résolu .....

;)

Lien vers le commentaire
Partager sur d’autres sites

PS : cela ne marche pas sur les tables myisam, mais de toute façon quasiment rien ne marche sur les tables myisam.

:francais:

(enfin faute de carton plus faible).

Les tables myISAM ont plusieurs intérêts, le principal étant qu'elles gèrent l'indexation sur les champs textes ce que ne peut faire le moteur innoDB (il ne peut indexer que des champs "chiffre") est cela peut devenir très important en terme de performance quand tu doit faire une recherche textuel.

Par exemple si tu plusieurs millier de sorte de fruit et que tu veux tout les fruit commençant par 'a' le temps de réponse à ce genre de requête serait beaucoup plus rapide avec une table type fruit en myISAM, ou si tu voulais être sur de ne pas avoir 2 type de fruit "pomme" (cote mysql) seul une clef unique sur ton type nomdufruit de ta table type fruit pourrait te le garantir et cela n'est pas possible avec une table innoDB.

Cela dit cela dépasse très largement le cadre de la question de ce post, mais les tables myISAM peuvent être très utiles.

Lien vers le commentaire
Partager sur d’autres sites

PS : cela ne marche pas sur les tables myisam, mais de toute façon quasiment rien ne marche sur les tables myisam.

:francais:

(enfin faute de carton plus faible).

Les tables myISAM ont plusieurs intérêts, le principal étant qu'elles gèrent l'indexation sur les champs textes ce que ne peut faire le moteur innoDB (il ne peut indexer que des champs "chiffre") est cela peut devenir très important en terme de performance quand tu doit faire une recherche textuel.

Par exemple si tu plusieurs millier de sorte de fruit et que tu veux tout les fruit commençant par 'a' le temps de réponse à ce genre de requête serait beaucoup plus rapide avec une table type fruit en myISAM, ou si tu voulais être sur de ne pas avoir 2 type de fruit "pomme" (cote mysql) seul une clef unique sur ton type nomdufruit de ta table type fruit pourrait te le garantir et cela n'est pas possible avec une table innoDB.

Cela dit cela dépasse très largement le cadre de la question de ce post, mais les tables myISAM peuvent être très utiles.

No probleme pour moi .....

S'il faut j'édite le sujet .. !! :-)

Lien vers le commentaire
Partager sur d’autres sites

Je ne savais pas cela effectivement.

Après ce n'est jamais très recommandé de faire des recherches full text en sql. Si à la modélisation on fait le choix de sacrifier les contraintes d'intégrité pour gagner en performance sur des recherches sur champ texte, c'est aussi que le choix technologique de base est IMHO inadapté au besoin de l'appli.

Lien vers le commentaire
Partager sur d’autres sites

Archivé

Ce sujet est désormais archivé et ne peut plus recevoir de nouvelles réponses.

×
×
  • Créer...