C中的随机播放功能

时间:2010-11-17 13:25:46

标签: c

随机播放功能定义为

Shuffle( A[n-1],A[n-2].....A[1],A[0]) = A[n-2]A[n-3]......A[1],A[0],A[n-1]

其中A [i]中的i表示数组中索引的二进制表示中的第I位。

例如,数组中第三个元素的shuffle是第五个数组元素。即..

随机(A [010])= A [100]。 (假设数组大小为8个元素)

我们看到第n-1位'0'被左旋转。因此A [4]的值被复制到A [2]中。我们可以在不使用数组中所有元素的临时数组的情况下执行此操作...

我想在简单的普通C中实现这个功能,但我只是无法理解如何更改位...

建议请...

4 个答案:

答案 0 :(得分:1)

您是否考虑过Knuth Shuffle

以下是来自RosettaCode的C中的示例:

#include <stdlib.h>
#include <string.h>

int rrand(int m)
{
  return (int)((double)m * ( rand() / (RAND_MAX+1.0) ));
}

#define BYTE(X) ((unsigned char *)(X)) 
void shuffle(void *obj, size_t nmemb, size_t size)
{
  void *temp = malloc(size);
  size_t n = nmemb;
  while ( n > 1 ) {
    size_t k = rrand(n--);
    memcpy(temp, BYTE(obj) + n*size, size);
    memcpy(BYTE(obj) + n*size, BYTE(obj) + k*size, size);
    memcpy(BYTE(obj) + k*size, temp, size);
  }
  free(temp);
} 

答案 1 :(得分:0)

您可以使用按位逻辑运算符&|等来更改位。您可以使用shift <<>>运算符移动位。

使用临时数组执行此操作最简单,否则如何避免覆盖以后需要的值?

答案 2 :(得分:0)

我不记得我在哪里找到了这种方法(可能是“C中的数字食谱”,但我不能在那里伪装)。

方法使用bit reversed shuffle(我在这里将它命名为“bitrev”),它重新排序元素索引abcdef变为fedcba的数组元素(字母代表位,6位示例)。三位恢复可以完成您的功能:

  1. 使用两个bitrev到两半数组,因此索引abcdef变为afedcb(当你对数组最高索引位的一半上的bitrev进行操作时保持不变);

  2. 在整个数组上使用bitrev,因此索引afedcb变为bcdefa,这就是您所需要的。

  3. 由于bitrev很容易在现场实施,所以你的工作。

答案 3 :(得分:-1)

//此函数具有复杂度O(N)

void shuffle(char *p, unsigned int pSize)
{
        unsigned int i = 0;
        for(i=0 ; i < (pSize - 1); i++)
        {
        char lTmpChar=p[i];
        p[i]=p[i+1];
        p[i+1]=lTmpChar;
        }
}

或使用模板(c ++):

template <typename T> void shuffle(T *p, unsigned int pSize)
{
        unsigned int i = 0;
        for(i=0 ; i < (pSize - 1); i++)
        {
        T lTmpChar=p[i];
        p[i]=p[i+1];
        p[i+1]=lTmpChar;
        }
}

您可以使用带有索引的shuffle函数,该索引是char数组,例如:

int arraySize = 10;
char array[arraySize]='abcdefghil';
char index[4]='0010';
int shuffled_index = atoi(shuffle(index,4));
if(shuffled_index < arraySize) // note that shuffled_index is not always valid
{
printf("Char: %c", array[shuffled_index]);
}