【问题标题】:Select rows with dynamic names from different table as column name in new table matched by articleId从不同的表中选择具有动态名称的行作为articleId匹配的新表中的列名
【发布时间】:2015-01-09 02:37:54
【问题描述】:

假设我有以下两个表

CREATE TABLE `articles` (
 `id` int(11) NOT NULL AUTO_INCREMENT,
 `artId` int(11) NOT NULL,
 `price` float NOT NULL,
 PRIMARY KEY (`id`),
 UNIQUE KEY `artId` (`artId`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1

CREATE TABLE `priceHistory` (
 `id` int(11) NOT NULL AUTO_INCREMENT,
 `artId` int(11) NOT NULL,
 `price` float NOT NULL,
 `checkdate` datetime NOT NULL,
 PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1

还有以下数据

INSERT INTO `test`.`articles` (`id`, `artId`, `price`) VALUES (NULL, '1', '5'), (NULL, '2', '2'), (NULL, '3', '3'), (NULL, '4', '9.50'), (NULL, '5', '1.3');


INSERT INTO `test`.`priceHistory` (`id`, `artId`, `price`, `checkdate`) VALUES (NULL, '1', '5', '2014-11-10 04:19:56'), (NULL, '1', '8.50', '2014-11-09 04:19:56'), (NULL, '1', '2.5', '2014-11-08 04:19:56'), (NULL, '2', '2', '2014-11-10 04:19:56'), (NULL, '2', '2.5', '2014-11-09 04:19:56'), (NULL, '3', '3', '2014-11-10 04:19:56'), (NULL, '4', '9.50', '2014-11-10 04:19:56'), (NULL, '4', '10', '2014-11-09 04:19:56'), (NULL, '4', '8', '2014-11-08 04:19:56'), (NULL, '4', '7', '2014-11-07 04:19:56'), (NULL, '5', '1.3', '2014-11-10 04:19:56'), (NULL, '5', '2', '2014-11-09 04:19:56');

我现在想做的是以下。我想从表articles 中选择所有文章,并且每个价格变化/价格历史条目都在同一行中。例如,最终结果应如下所示:

id  articleId   currentPrice    2014-11-07        2014-11-08    2014-11-09      2014-11-10
1   1           5               NULL              2.5               8.5             5
2   2           2               NULL              NULL              2.5             2
3   3           3               NULL              NULL              NULL            3
4   4           9.5             7                 8                 10              9.5
5   5           1.3             NULL              NULL              2               1.3

基本上,我想从另一个表中选择日期并将它们作为列名放入并相应地填写数据。这在某种程度上可能与 SELECT 一起使用吗?我在这个主题上找到了多个资源,但它们要么用于固定数量的行,我需要它使其具有动态性,因为日期时间可能会持续到明年(极端示例),或者它们只用于一个表。这些是我找到的资源

  1. Problems to select the correct row from a second table
  2. Using MySQL GROUP_CONCAT or PIVOT on multiple joined tables
  3. MySQL - How to display row value as column name using concat and group_concat
  4. Select dynamic Columns in mysql
  5. mysql select dynamic row values as column names, another column as value
  6. Mysql query to dynamically convert rows to columns
  7. MySQL - Rows to Columns
  8. http://buysql.com/mysql/12-how-to-pivot-tables.html

【问题讨论】:

  • 您已经尝试过什么了吗?我认为可以通过先查询日期来完成,然后将它们添加到您要检索的字段中。
  • 嗨,不幸的是我没有真正尝试任何东西。我使用了帖子底部提供的链接中的代码示例,但它们太复杂了,我无法理解或使它们适用于多个表。正如我上面所说,这些示例都仅适用于一个表(也适用于我!)或有限数量的行而不是动态数量。
  • 这个论坛是关于I tried it this way but it doesn't work where do I go wrong 它不是I have no clue what I am doing can you supply me with correct code。您不能指望人们浏览您提供的所有链接中的所有代码,而您自己却没有付出任何努力。但也许你会很幸运。与此同时,尝试一些东西,分享你的代码。对于初学者,我不会节省时间,只是日期。
  • 我可以发布我尝试过的东西,但这并不重要,因为我尝试的是具有一个表或固定数量的行/列的数据库,而不是动态/多个。我不知道你为什么会有这样的消极情绪。我还提供了许多链接作为来源,我查看并尝试了这些链接。你还想要什么?我还为数据库提供了数据。你表现得就像我刚问过,什么也没提供。
  • 您是否介意分享一下使用多列而不是对行进行操作的背后的想法?

标签: mysql sql


【解决方案1】:

好吧,您应该付出更多努力来尝试调整您为您的案例找到的解决方案之一,或者如果您不理解那里的某些内容 - 更加努力,询问您不理解的具体内容 -如何连接两个表,如何连接字符串,如何在 MySQL 中使用变量等等,学习这些东西是如何工作的。

也就是说,让我们以 solution #6 为例 - Mysql query to dynamically convert rows to columns,并根据您的情况进行调整。

SET @sql = NULL;

SELECT
  GROUP_CONCAT(
    DISTINCT CONCAT(
      'MAX(IF(CAST(checkdate AS date) = ''', CAST(checkdate AS date), ''', h.price, NULL)) AS ', '`', CAST(checkdate AS date), '`'
    )
    ORDER BY checkdate
  )
INTO
  @sql
FROM
  priceHistory;

SET @sql = CONCAT('
  SELECT
    a.id AS articleId,
    a.price AS currentPrice,
    ', @sql, '
  FROM
    articles a LEFT JOIN priceHistory h
  ON
    a.id = h.artId
  GROUP
    BY a.id
');

PREPARE stmt FROM @sql;

EXECUTE stmt;

等等!

+-----------+--------------+------------+------------+------------+--------------------+
| articleId | currentPrice | 2014-11-07 | 2014-11-08 | 2014-11-09 | 2014-11-10         |
+-----------+--------------+------------+------------+------------+--------------------+
|         1 |            5 |       NULL |        2.5 |        8.5 |                  5 |
|         2 |            2 |       NULL |       NULL |        2.5 |                  2 |
|         3 |            3 |       NULL |       NULL |       NULL |                  3 |
|         4 |          9.5 |          7 |          8 |         10 |                9.5 |
|         5 |          1.3 |       NULL |       NULL |          2 | 1.2999999523162842 |
+-----------+--------------+------------+------------+------------+--------------------+

在您的数据结构中需要修复三件事。

  1. articles 中删除artId - 这是完全多余的。
  2. checkdate的类型更改为date
  3. 千万不要用float存钱(看看值1.2999999523162842),改用NUMERIC

【讨论】:

  • 嗨。对于db结构:1.我的文章ID只是示例,在现实世界中它们与主键不同,也是数据提取所需的2.完成3.完成,非常感谢!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2012-05-20
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-02-09
  • 1970-01-01
相关资源
最近更新 更多