想象一下 PostgreSQL 9.0 上具有以下结构的表:
create table raw_fact_table (text varchar(1000));
为了简单起见,我只提到一个文本列,实际上它有十几个。该表有 100 亿行,每列有很多重复项。该表是使用 COPY FROM 从平面文件 (csv) 创建的。
为了提高性能,我想转换为以下星型模式结构:
create table dimension_table (id int, text varchar(1000));
然后,事实表将被替换为如下所示的事实表:
create table fact_table (dimension_table_id int);
我目前的方法基本上是运行以下查询来创建维度表:
Create table dimension_table (id int, text varchar(1000), primary key(id));
然后创建填充我使用的维度表:
insert into dimension_table (select null, text from raw_fact_table group by text);
之后我需要运行以下查询:
select id into fact_table from dimension inner join raw_fact_table on (dimension.text = raw_fact_table.text);
试想一下,通过将所有字符串与所有其他字符串进行多次比较,我得到的可怕性能。
在 MySQL 上,我可以在 COPY FROM 期间运行存储过程。这可以创建字符串的散列,并且所有后续字符串比较都在散列而不是长原始字符串上完成。这在 PostgreSQL 上似乎是不可能的,那我该怎么办?
示例数据将是一个 CSV 文件,其中包含类似这样的内容(我也在整数和双精度数周围使用引号):
"lots and lots of text";"3";"1";"2.4";"lots of text";"blabla"
"sometext";"30";"10";"1.0";"lots of text";"blabla"
"somemoretext";"30";"10";"1.0";"lots of text";"fooooooo"