Requête de tableau croisé dynamique MySQL à colonne dynamique
P粉262113569
P粉262113569 2023-08-27 17:24:10
0
2
366

J'utilise le tableau suivant pour stocker les données produit :

mysql> SELECT * FROM produit ; +--------------+---------------+--------+ | identifiant nom | description | +--------------+---------------+--------+ | 1 | produit1 | premier produit | | 2 | produit2 | deuxième produit | 5 | +--------------+---------------+--------+ mysql> SELECT * FROM product_additional; +-----------------+----------------+ | identifiant | nom du champ | +-----------------+----------------+ | 1 | | 1 | hauteur | 103 | | 2 | | 2 | hauteur 13 | | 2 | couleur noir | +-----------------+----------------+

Utilisez la requête suivante pour sélectionner des enregistrements dans deux tables

mysql> p.id ,p.nom , p.description ,MAX(IF(pa.fieldname = 'size', pa.fieldvalue, NULL)) comme `size` ,MAX(IF(pa.fieldname = 'height', pa.fieldvalue, NULL)) comme `hauteur` ,MAX(IF(pa.fieldname = 'color', pa.fieldvalue, NULL)) comme `color` DE produit p LEFT JOIN product_additional AS pa ON p.id = pa.id GROUPER PAR p.id +--------------+---------------+--------+-------- -+--------+ | identifiant nom | description | taille | +--------------+---------------+--------+-------- -+--------+ | 1 | produit1 | premier produit | | 2 | produit2 | deuxième produit | L | +--------------+---------------+--------+-------- -+--------+ 

Tout va bien :)

Puisque je remplis la table "append" de manière dynamique, ce serait formidable si la requête était également dynamique. De cette façon, je n'ai pas besoin de modifier la requête à chaque fois que j'entre un nouveau nom de champ et une nouvelle valeur de champ.

P粉262113569
P粉262113569

répondre à tous (2)
P粉604848588

Mon approche est légèrement différente de la réponse acceptée. De cette façon, vous évitez d'utiliser GROUP_CONCAT, qui a une limite par défaut de 1024 caractères, ce qui ne fonctionnera pas si vous avez beaucoup de champs à moins que vous ne modifiiez la limite.

SET @sql = ''; SELECT @sql := CONCAT(@sql,if(@sql='','',', '),temp.output) FROM ( SELECT DISTINCT CONCAT( 'MAX(IF(pa.fieldname = ''', fieldname, ''', pa.fieldvalue, NULL)) AS ', fieldname ) as output FROM product_additional ) as temp; SET @sql = CONCAT('SELECT p.id , p.name , p.description, ', @sql, ' FROM product p LEFT JOIN product_additional AS pa ON p.id = pa.id GROUP BY p.id, p.name, p.description'); PREPARE stmt FROM @sql; EXECUTE stmt; DEALLOCATE PREPARE stmt;

Cliquez ici pour voir la démo

    P粉495955986

    La seule façon de faire cela de manière dynamique dans MySQL est d'utiliser des instructions préparées. Voici un excellent article à leur sujet :

    Tableau croisé dynamique (convertir les lignes en colonnes)

    Votre code ressemblera à ceci :

    SET @sql = NULL; SELECT GROUP_CONCAT(DISTINCT CONCAT( 'MAX(IF(pa.fieldname = ''', fieldname, ''', pa.fieldvalue, NULL)) AS ', fieldname ) ) INTO @sql FROM product_additional; SET @sql = CONCAT('SELECT p.id , p.name , p.description, ', @sql, ' FROM product p LEFT JOIN product_additional AS pa ON p.id = pa.id GROUP BY p.id, p.name, p.description'); PREPARE stmt FROM @sql; EXECUTE stmt; DEALLOCATE PREPARE stmt;

    VoirDémo

    Remarque : La fonction GROUP_CONCAT a une limite de longueur de 1 024 caractères. Afficher le paramètre group_concat_max_len

      Derniers téléchargements
      Plus>
      effets Web
      Code source du site Web
      Matériel du site Web
      Modèle frontal
      À propos de nous Clause de non-responsabilité Sitemap
      Site Web PHP chinois:Formation PHP en ligne sur le bien-être public,Aidez les apprenants PHP à grandir rapidement!