一个简单的公式

时间:2010-10-23 09:41:14

标签: algorithm formula

我有一个for循环,给出一个给定的整数序列,对于固定参数N和D:

    int i = 0, j = 0;
    for (int k=0; k<N; k++) {             
      sequence[k] = i;
      if ((i += D) >= N) i = ++j;
    }

我想找到一个简单的公式来重现这个序列,只取决于N和D(和索引k),如sequence[k] = D*(k%D)+ k/D(这不起作用)。我努力了但是我找不到总能适用于N和D的任何值的东西!

谢谢!

3 个答案:

答案 0 :(得分:1)

这是公式。目前它需要一个条件语句,但如果你想要纯函数形式,你总是可以通过一个返回0或1的函数来表达它。

我把它写成Perl函数,以便于测试(我测试了所有N&lt; = 20和D介于0和N之间)

sub div { my ($x, $y) = @_; return ($x-$x%$y)/$y }; # whole division

my $small_subsequence_length = div($N, $D);
my $big_subsequence_length = $small_subsequence_length + 1;
my $num_big_subseqiences = $N % $D;
my $num_total_big_subsequence_numbers = $big_subsequence_length * $num_big_subseqiences;
my $num_total_small_subsequence_numbers = $N - $num_total_small_subsequence_numbers;
my $num_small_subseqiences = div($num_total_small_subsequence_numbers, $small_subsequence_length);

sub sequence {
    my $k = $_[0];
    my ($subsequence_num, subsequence_offset);

    if ($k > $num_total_big_subsequence_numbers) {
        my $k2 = $k - $num_total_big_subsequence_numbers;
        $subsequence_num = div($k2, $small_subsequence_length) + $num_big_subseqiences;
        $subsequence_offset = ($k2 % $small_subsequence_length) * $D;
    } else {
        $subsequence_num = div($k, $big_subsequence_length);
        $subsequence_offset = ($k % $big_subsequence_length) * $D;
    }
    return $subsequence_offset + $subsequence_num;
}

答案 1 :(得分:1)

将DVK的功能转换为C代码,并删除了分支:

int sequence(int N, int D, int k) {
    int subsequence_length = N / D + 1;
    int num_big_subseqiences = N % D;
    int num_total_big_subsequence_numbers = subsequence_length * num_big_subseqiences;

    int small = (k > num_total_big_subsequence_numbers) & 1;

    k -= num_total_big_subsequence_numbers * small;
    subsequence_length -= small;
    subsequence_num = (k / subsequence_length) + num_big_subseqiences * small;
    subsequence_offset = (k % subsequence_length) * D;

    return subsequence_offset + subsequence_num;
}

答案 2 :(得分:0)

我认为以下情况应该:

sequence[0] = 0;

For k!=0,
sequence[k] = (sequence[k-1]+D)%N;
sequence[k] = ( (temp=(sequence[k-1]+D)) / N)? ++sequence[0]: temp%N;

这里,temp是一个临时变量,用于避免RHS中表达式的冗余。

我知道这很复杂,但我确信这是正确的。 设置完所有值后,您可以将序列[0]重置为0,然后就可以了。

PS:我正试图获得一个封闭的表格。