2013-04-04 66 views
0

我有以下HSQLDB模式:为什么我的HSQLDB表格在磁盘上占用太多空间?

CREATE TABLE RUNSTATS 
(
    ID  BINARY(16) NOT NULL, 
    ENTITY BLOB(128K)  NOT NULL 
    ,CHECK (PUBLIC.RUNSTATS.ID IS NOT NULL) 
    ,CHECK (PUBLIC.RUNSTATS.ENTITY IS NOT NULL) 
); 

ALTER TABLE RUNSTATS 
    ADD CONSTRAINT pk_runstats 
    PRIMARY KEY (ID); 

CREATE TABLE RUNSTATS__AVGLATENCYINDEX 
(
    ID   BINARY(16), 
    TIMESTAMP BIGINT, 
    FLOWID  VARCHAR(200), 
    AVGLATENCY DOUBLE 
); 

ALTER TABLE RUNSTATS__AVGLATENCYINDEX 
    ADD CONSTRAINT pk_runstats__avglatencyindex 
    PRIMARY KEY (ID, FLOWID); 

CREATE INDEX IDX_RUNSTATS__AVGLATENCYINDEX_FLOWID 
    ON RUNSTATS__AVGLATENCYINDEX (FLOWID ASC); 

的RUNSTATS表是x.lobs文件和RUNSTATS__AVGLATENCYINDEX - 在x.data

我插入RUNSTATS对象,其中每个在RUNSTATS表中产生1行,在RUNSTATS__AVGLATENCYINDEX中产生100行。我运行三个会话,插入100,1000和10000 RunStats对象。

另一个非常重要的细节 - 实际流ID值都正好是20个英文字符长,尽管字段为VARCHAR(200)

请在下面找到x.data文件的磁盘使用情况汇总(含在RUNSTATS__AVGLATENCYINDEX表):

  1. 10,000行= 2.0MB
  2. 100,000行= 16MB
  3. 1,000,000行= 128MB

查阅原始计算: (整型尺寸(ID)+整型尺寸(流ID)+整型尺寸(时间戳)+整型尺寸(AVGLATENCY))= 16 + 20 + 8 + 8 = 52

所以1,000,000行应大约需要52 * 1,000,000 =〜50MB

最佳尺寸比实际少两倍多。

这是正常的数据库开销吗?我可以指示hsqldb引擎更有效地利用空间吗?

多一点背景:

  • 实体只添加(不会被删除)
  • 有当实体以规则的步伐,增加了一个明确的期限。例如,每10秒钟3天。之后 - 不再添加实体。

编辑

请在这里找到压缩脚本文件 - https://docs.google.com/file/d/0B2pbsdBJxJI3Z2dFTndMZnBMU2c/edit?usp=sharing

回答

1

我插入1,000,000行到RUNSTATS__AVGLATENCYINDEX表和.data文件的大小为128MB。额外的大小是由于表中的主键和额外索引(32字节)以及行,字符串和可空性信息的长度。 FLOWID列使用20 + 5个字节。每行总共需要32 + 12 + 4字节的额外空间,因此总数为100字节。这被放大到32字节的倍数(FILE SCALE),导致每行128字节。

检查您的.script文件。如果你有SET FILE SCALE 256或更高,这可能解释额外的空间。每行的大小是此SCALE值的倍数。

使用默认的SCALE 32和给定的FLOWID大小,每行应该使用128个字节。

您还可以在数据库中执行SHUTDOWN COMPACT,看看大小是什么,被删除的行已被删除后。

您已经添加了一个链接到一个.script文件。 SET TABLE ...语句在大表中表示751700行。每行在磁盘上占用128个字节。

SET FILES SCALE 32 
... 
CREATE CACHED TABLE PUBLIC.RUNSTATS(ID BINARY(16) NOT NULL PRIMARY KEY,ENTITY BLOB(128K) NOT NULL) 
CREATE CACHED TABLE PUBLIC.RUNSTATS__AVGLATENCYINDEX(ID BINARY(16),TIMESTAMP BIGINT,FLOWID VARCHAR(200),AVGLATENCY DOUBLE,PRIMARY KEY(ID,FLOWID)) 
CREATE INDEX IDX_RUNSTATS__AVGLATENCYINDEX_FLOWID ON PUBLIC.RUNSTATS__AVGLATENCYINDEX(FLOWID) 
... 
SET TABLE PUBLIC.RUNSTATS INDEX '4021 0 7517' 
SET TABLE PUBLIC.RUNSTATS__AVGLATENCYINDEX INDEX '4039 79 0 0 751700' 
+0

只有添加的行,没有删除。但我跑了SHUTDOWN COMPACT - 没有任何效果,正如预期的那样。我可以在脚本文件中看到“SET FILES SCALE 32”。 – mark 2013-04-05 01:51:49

+0

也许你有其他表格,或者表格较大。检查.script文件以查找“SET TABLE xxx INDEX nn nn nn'语句。最后一个数字是表格的行数。 – fredt 2013-04-05 11:23:01

+0

你是对的,愚蠢的我。还有一张桌子。我将从模式中删除它,重新运行整个测试,然后更新问题。 – mark 2013-04-05 11:48:49