perl中的数组访问复杂度为O(1)还是O(n)?

时间:2012-11-29 17:40:30

标签: perl caching complexity-theory

我正在缓存函数f(1),f(2),...,f(1e7)的结果。缓存中的元素将随机读取。在C中,我将其存储在向量中,因为访问复杂度为O(1)。在Perl中,我应该将缓存存储在向量还是哈希?

我觉得将它存储在哈希中并不会利用输入是连续整数的事实。但另一方面,我可能会过度思考这一点。

4 个答案:

答案 0 :(得分:7)

不要自己缓存函数的结果,而是使用为您处理它的Memoize core module

use Memoize;
memoize('slow_function');
slow_function(arguments); # Is faster than it was before

这就是它的全部内容,它已存在很长时间并经过充分测试。

答案 1 :(得分:2)

除了通常的免责声明关于效率的担忧,直到你描述,我会说它存储在一个数组中。哈希在计算哈希密钥时会产生额外的开销。此外,数组是最自然的表示形式,除非你知道你的表现没有,否则为了清晰起见。

答案 2 :(得分:1)

Perl中的数组和散列都是O(1)。但是,我敢打赌,阵列的O(1)在绝对时钟时间上更快。在后序整数的情况下,数组可能比其简单的索引数学更快。

答案 3 :(得分:0)

访问存在的数组元素比插入哈希更快。从好的方面来说,两者的表现同样相称。 (复杂性分析衡量某些东西的缩放程度,而不是它的速度。)

数组元素的最坏情况访问:

$x = $a[$i];           # O(1)
$a[$i] = $x;   $i<@a   # O(1)
$a[$i] = $x;           # O(1), amortized

哈希元素的最坏情况访问(对于有限长度的键):

$x = $h{$k};           # O(1)
$h{$k} = $x;           # O(1), amortized

(“摊销的O(1)”表示这些操作中的N为O(N)。)

鉴于你的键是连续的整数,你绝对应该使用数组。

my @cache;
sub func {
    my ($n) = @_;
    return $cache[$n] //= ...;
}

如果您的密钥稀疏,那么最好使用散列来节省内存。

my %cache;
sub func {
    my ($n) = @_;
    return $cache{$n} //= ...;
}