I have a table like this:
+------+-----------+
|caseID|groupVarian|
+------+-----------+
|1 |A,B,C,D,E |
+------+-----------+
|2 |A,B,N,O,P |
+----
Basically, you want to enumerate the variants. If you just want a number, then you could use the minimum id:
select t.*, min_codeId as groupVariantId
from t join
(select groupVariant, min(codeId) as min_codeId
from t
group by groupVariant
) g
on t.groupVariant = g.groupVariant;
But that is not quite what you want. You appear to want them enumerated by the order they appear in the data. For that, you need variables. This is a bit tricky, but:
select t.*, rn as groupVariantId
from t join
(select g.*,
(@rn := if(@gv = groupvariant, @gv,
if(@gv := groupvariant, @gv+1, @gv+1)
)
) as rn
from (select groupVariant, min(codeId) as min_codeId
from t
group by groupVariant
order by min(codeId)
) g cross join
(select @gv := '', @rn := 0) params
) g
on t.groupVariant = g.groupVariant;
Using variables is tricky. One important consideration: MySQL does not guarantee the order of evaluation of expressions in a SELECT
. That means that a variable should not be assigned in one expression and then used in another -- because they could be evaluated in the wrong order (another answer has this mistake).
In addition, the order by
needs to take place in a subquery. MySQL does not guarantee that the variable assignment occurs before the sorting.