我有一个用户条目表,对于每个条目,我都有一个(2字节)整数数组来存储(15-25,零星甚至更多)。数组元素将同时被写入和读取,永远不需要更新或单独访问它们。他们的订单很重要将其视为数组对象是有道理的。
我有数百万这些用户条目,并希望以尽可能少的磁盘空间存储它。然而,我正在努力解决MySQL缺少Array
数据类型的问题。
我一直在考虑以下选项。
my_data
,user_id
和data_id
列创建一个表data_int
。为了提高效率,需要user_id
上的索引,每个整数总共超过10个字节。在MySQL中有更好的方法吗?我知道MySQL有一个高效的varchar
类型,所以理想情况下我将我的2字节整数存储为varchar
中的2字节字符(或与blob
类似的方法),但是我不知道该怎么做。这可能吗?该怎么做?
答案 0 :(得分:0)
您可以将它们存储为单独的SMALLINT NULL
列。
在MyISAM中,这对每个值使用2个字节的数据+ 1个空指示符。
在InnoDB中,空指示符被编码到列的字段起始偏移中,因此它们不占用任何额外空间,并且空值实际上不存储在行数据中。如果行足够小,所有偏移量都是1个字节,则每个现有值使用3个字节(1个字节偏移量,2个字节数据),每个不存在的值使用1个字节。
这些中的任何一个都比使用INT
具有特殊值来表示它不存在更好,因为对于每个值,这将是4个字节的数据。
答案 1 :(得分:0)
评论中给出了最佳答案,因此我将在此处重新发布一些使用准备好的代码,以供进一步参考。
MySQL有一个varbinary
类型可以很好地解决这个问题:你可以简单地使用PHP的pack
/ unpack
函数将它们转换成二进制形式,以及使用varbinary
将二进制表单存储在数据库中。转换的示例代码如下。
function pack24bit($n) { //input: 24-bit integer, output: binary string of length 3 bytes
$b3 = $n%256;
$b2 = $n/256;
$b1 = $b2/256;
$b2 = $b2%256;
return pack('CCC',$b1,$b2,$b3);
}
function unpack24bit($packed) { //input: binary string of 3 bytes long, output: 24-bit int
$arr = unpack('C3b',$packed);
return 256*(256*$arr['b1']+$arr['b2'])+$arr['b3'];
}