好的,请原谅这个有点奇怪的例子,但我无法想到更好的东西,而我真正的SQL查询会使真正问题的本质过于复杂......
让我想象我有3个表: - 人(PersonID,PersonName,DoB等) - PersonItemKey(PersonItemKeyID,ItemName) - PersonItemValue(PersonItemValueID,PersonItemKeyID,PersonID,Value)
因此,我们可以为"袜子","跳线"," T恤和项目值提供物品键,表示特定的人说有10对袜子,6个套头衫和8件衬衫。
我可以通过以下查询获取此信息:
SELECT *
FROM Person
LEFT JOIN PersonItemValue ON PersonItemValue.PersonID = Person.PersonID
INNER JOIN PersonItemKey ON PersonItemValue.PersonItemKeyID = PersonItemKey.PersonItemKeyID
问题是这将返回3行,每行包含相同的PersonID,Name,DoB等,但具有不同的ItemName和Value字段(一个用于袜子,一个用于跳线,一个用于衬衫)。
是否可以返回单行,并将字段名称和值的键提升为其值。即使它成为" Socks"成为一个字段名称,10是它的值,"跳线"是另一个以6为价值的领域,"衬衫"作为另一个值为8的字段?
我已经设法用PHP中的代码执行此操作:
$sql = "SELECT *
FROM Person
LEFT JOIN PersonItemValue ON PersonItemValue.PersonID = Person.PersonID
INNER JOIN PersonItemKey ON PersonItemValue.PersonItemKeyID = PersonItemKey.PersonItemKeyID";
// Run the query
$query = $db->query($sql);
// Convert it to a map
$allrows = array();
while($row = $query->fetch(PDO::FETCH_ASSOC))
{
// Create the entry if it doesn't exist
$key = $row['PersonID'];
if (isset($allrows[$key]) == false)
{
$allrows[$key] = $row;
}
// Turn ItemName into a field, and set its value
$field_name = $row['ItemName'];
$field_value = $row['Value'];
// Put the metric into the row
$allrows[$key][$field_name] = $field_value;
}
但在查询本身中做得更好。
这可能吗?
提前致谢。
P.S。我不相信这是MySQL pivot row into dynamic number of columns的副本,因为它使用了聚合函数(count)。至少我无法在我的案例中使用它。