给出如此数据结构:
CREATE TABLE records (
id INT PRIMARY KEY AUTO_INCREMENT,
name VARCHAR(255) NOT NULL
);
CREATE TABLE records_data (
id INT PRIMARY KEY AUTO_INCREMENT,
record_id INT NOT NULL,
record_data_type_id INT NOT NULL,
data VARCHAR(255),
UNIQUE(record_id, record_data_type_id)
);
CREATE TABLE records_data_types (
id INT PRIMARY KEY AUTO_INCREMENT,
name VARCHAR(255) NOT NULL UNIQUE
);
和(样本)数据如下:
INSERT INTO records_data_types (name) VALUES ('Location');
INSERT INTO records_data_types (name) VALUES ('Ice Cream Flavor');
INSERT INTO records_data_types (name) VALUES ('Slogan');
INSERT INTO records_data_types (name) VALUES ('Starting Pay');
INSERT INTO records_data_types (name) VALUES ('Grand Opening Date');
INSERT INTO records (name) VALUES ('Business A');
INSERT INTO records (name) VALUES ('Business B');
INSERT INTO records (name) VALUES ('Business C');
INSERT INTO records (name) VALUES ('Business D');
INSERT INTO records_data (record_id, record_data_type_id, data) VALUES (1, 1, 'New York, NY');
INSERT INTO records_data (record_id, record_data_type_id, data) VALUES (1, 2, 'Chocolate');
INSERT INTO records_data (record_id, record_data_type_id, data) VALUES (1, 3, 'The only apple!');
INSERT INTO records_data (record_id, record_data_type_id, data) VALUES (1, 4, '27');
INSERT INTO records_data (record_id, record_data_type_id, data) VALUES (1, 5, '2017-09-01');
INSERT INTO records_data (record_id, record_data_type_id, data) VALUES (2, 1, 'Chicago, IL');
INSERT INTO records_data (record_id, record_data_type_id, data) VALUES (2, 2, 'Vanilla');
INSERT INTO records_data (record_id, record_data_type_id, data) VALUES (2, 3, 'Windy and tasty');
INSERT INTO records_data (record_id, record_data_type_id, data) VALUES (2, 4, '10');
INSERT INTO records_data (record_id, record_data_type_id, data) VALUES (2, 5, '2017-01-01');
INSERT INTO records_data (record_id, record_data_type_id, data) VALUES (3, 1, 'Seattle, WA');
INSERT INTO records_data (record_id, record_data_type_id, data) VALUES (3, 2, 'Rocky Road');
INSERT INTO records_data (record_id, record_data_type_id, data) VALUES (3, 5, '2011-05-14');
INSERT INTO records_data (record_id, record_data_type_id, data) VALUES (4, 2, 'Mint Chip');
INSERT INTO records_data (record_id, record_data_type_id, data) VALUES (4, 3, 'Toothpaste and orange juice');
我希望获得一个透视结果集,其中列标题为records_data_types.name
,每行都属于record
条目。
对于每个条目,我希望得到:
SELECT
records.name as RecordName,
records_data_types.name as DataType,
records_data.data as Data
FROM records_data
INNER JOIN records
ON records_data.record_id = records.id
INNER JOIN records_data_types
ON records_data_types.id=records_data.record_data_type_id
WHERE records.id = ? -- for each record, pivoted;
这些数据是由代码处理的(在这种情况下是PHP,但它并不重要,所以使用该查询来收集数据,然后使用代码将结果集配置为记录与数据关系的记录数组。
我正在使用MySQL和SQL Server(2005),并且已经将PIVOT运算符与SQL服务器一起使用,但这会导致性能下降(这是一个相当庞大的数据库)。
这里主要关注的是我绝对可以将每个记录作为子查询获取,但最终(并且在实际生产情况下)使用10-20个数据项拉出更大的记录集(可能是300多条记录)会产生非常大的数量数据(3000-6000 +行)。
似乎最快的查询只是执行左连接,并通过代码格式化数据。子查询似乎是第二个(参见DB-Fiddle)
通过查看SO和其他地方的其他类似问题,似乎有很多方法可以使用PIVOT运算符,使用公共表表达式,临时表和/或子查询来执行此调整,但大多数依赖于在枢轴中的聚合(即通过max(数据)转动),但在这种情况下,它只是一对一的关系。对于任何一条记录,每种数据类型只有一个数据条目。
TLDR:有更好的方法可以优化this等查询吗?
谢谢!