Prova questa soluzione:
SELECT
a.product_group,
SUBSTRING_INDEX(GROUP_CONCAT(a.manufacturer ORDER BY a.occurrences DESC SEPARATOR ':::'), ':::', 1) AS manufacturer_mode
FROM
(
SELECT
aa.product_group,
aa.manufacturer,
COUNT(*) AS occurrences
FROM
products aa
GROUP BY
aa.product_group,
aa.manufacturer
) a
GROUP BY
a.product_group
Spiegazione:
Questo utilizza ancora una forma di sottoquery, ma che viene eseguita solo una volta rispetto a una che viene eseguita riga per riga come nel tuo esempio originale.
Funziona selezionando prima il product_group
id, il produttore e il conteggio di quante volte il produttore appare per ogni particolare gruppo.
Il FROM
sub-select avrà un aspetto simile dopo l'esecuzione (solo inventando i dati qui):
product_group | manufacturer | occurrences
---------------------------------------------------
1 | XYZ | 4
1 | Test | 2
1 | Singleton | 1
2 | Eloran | 2
2 | XYZ | 1
Ora che abbiamo il risultato della sottoselezione, dobbiamo scegliere la riga che ha il massimo nelle occurences
campo per ogni gruppo di prodotti.
Nella query esterna, raggruppiamo ancora una volta la sottoselezione in base al product_group
campo, ma questa volta solo il product_group
campo. Ora quando facciamo il nostro GROUP BY
qui, possiamo usare una funzione davvero interessante in MySQL chiamata GROUP_CONCAT
che possiamo usare per concatenare i produttori insieme e nell'ordine che vogliamo.
...GROUP_CONCAT(a.manufacturer ORDER BY a.occurrences DESC SEPARATOR ':::'...
Quello che stiamo facendo qui è concatenare i produttori che sono raggruppati per product_group
id, il ORDER BY a.occurrences DESC
fa in modo che il produttore con il maggior numero di apparenze appaia prima nell'elenco concatenato. Infine separiamo ogni produttore con :::
. Il risultato di questo per product_group
1
sarà simile a:
XYZ:::Test:::Singleton
XYZ
appare per primo poiché ha il valore più alto nella occurance
campo. Noi solo vuoi selezionare XYZ
, quindi racchiudiamo la concatenazione all'interno di SUBSTRING_INDEX
, che ci consentirà di selezionare solo il primo elemento dell'elenco in base al :::
delimitatore.
Il risultato finale sarà:
product_group | manufacturer_mode
---------------------------------------
1 | XYZ
2 | Eloran