次の表のようなものがあります。
================================================
| Id | UserId | FieldName | FieldValue |
=====+========+===============+================|
| 1 | 100 | Username | John Doe |
|----+--------+---------------+----------------|
| 2 | 100 | Password | pass123! |
|----+--------+---------------+----------------|
| 3 | 102 | Username | Jane |
|----+--------+---------------+----------------|
| 4 | 102 | Password | $ecret |
|----+--------+---------------+----------------|
| 5 | 102 | Email Address | [email protected] |
------------------------------------------------
次のような結果が得られるクエリが必要です。
==================================================
| UserId | Username | Password | Email Address |
=========+===========+===========================|
| 100 | John Doe | pass123! | |
|--------+-----------+----------+----------------|
| 102 | Jane | $ecret | [email protected] |
|--------+-----------+----------+----------------|
FieldNameの値は、ユーザー名、パスワード、および電子メールアドレスに限定されないことに注意してください。ユーザー定義なので、何でもかまいません。
SQLでこれを行う方法はありますか?
MySQLはANSI PIVOT/UNPIVOT構文をサポートしていないため、次のように使用します。
SELECT t.userid
MAX(CASE WHEN t.fieldname = 'Username' THEN t.fieldvalue ELSE NULL END) AS Username,
MAX(CASE WHEN t.fieldname = 'Password' THEN t.fieldvalue ELSE NULL END) AS Password,
MAX(CASE WHEN t.fieldname = 'Email Address' THEN t.fieldvalue ELSE NULL END) AS Email
FROM TABLE t
GROUP BY t.userid
ご覧のとおり、CASEステートメントは値ごとに定義する必要があります。これを動的にするには、 MySQLの準備済みステートメント(動的SQL)構文 を使用する必要があります。
GROUP_CONCAT を使用できます
(未試験)
SELECT UserId,
GROUP_CONCAT( if( fieldname = 'Username', fieldvalue, NULL ) ) AS 'Username',
GROUP_CONCAT( if( fieldname = 'Password', fieldvalue, NULL ) ) AS 'Password',
GROUP_CONCAT( if( fieldname = 'Email Address', fieldvalue, NULL ) ) AS 'Email Address',
FROM table
GROUP BY UserId