C中nxn矩阵的walsh表

C中nxn矩阵的walsh表,c,matrix,multidimensional-array,C,Matrix,Multidimensional Array,我一直在试图理解n维的沃尔什表矩阵,因为我需要编写一个代码来生成任意给定顺序的沃尔什矩阵。到目前为止,我还没有写出一个有效的代码。有人能帮我做一下算法吗,或者对我下面的程序提出一些建议:(它适用于2x2和4x4,但不适用于8x8) #包括 #包括 main() { /*程序变量 维度变量,n 循环变量i,j 沃尔什表a的二维数组[100][100]*/ int n,j,i,a[100][100]; clrsc(); //显示沃尔什表的用户输入 printf(“输入尺寸”); scanf(“%d”

我一直在试图理解n维的沃尔什表矩阵,因为我需要编写一个代码来生成任意给定顺序的沃尔什矩阵。到目前为止,我还没有写出一个有效的代码。有人能帮我做一下算法吗,或者对我下面的程序提出一些建议:(它适用于2x2和4x4,但不适用于8x8)

#包括
#包括
main()
{
/*程序变量
维度变量,n
循环变量i,j
沃尔什表a的二维数组[100][100]*/
int n,j,i,a[100][100];
clrsc();
//显示沃尔什表的用户输入
printf(“输入尺寸”);
scanf(“%d”和“&n”);
//将行从0迭代到“n”

对于(i=0;i您应该将沃尔什代码的生成视为一个递归问题。首先生成2x2;然后生成4x4,以此类推。每次,通过在右上象限和左下象限中添加两个低阶块的副本,并在右下象限中添加其逆项,从上一个块生成下一个块你可以通过创建一次矩阵,然后以增加块大小的方式通过它来实现。下面是它的工作原理

更新了,因此它生成了您在wiki上看到的
1-1
版本的代码

再次更新,使其能够获取矩阵大小的输入并生成任意大小的沃尔什矩阵;包括各种错误检查和其他酷技巧:

FINAL(?)UPDATERyker指出我的代码中有一个内存错误。我找到并修复了它-并用
valgrind
检查了它。它现在似乎工作正常

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

int **twoDmatrix(int m, int n) {
// create a 2D matrix of arbitrary dimensions
  int ii, **M;
  M = malloc(m * sizeof(int**));
  M[0] = malloc(m*n*sizeof(int*));
  for(ii=1; ii<m; ii++) {
    M[ii] = M[0] + ii * n;
  }
  return M;
}

void free2D(int** M) {
// free memory allocated by twoDmatrix()
  free(M[0]);
  free(M);
}

int isPow2(int n) {
// return 1 if the argument is a valid (positive) power of 2
  if(n<=1) return 0;
  while(n>1) {
    if (n%2==1) return 0;
    n = n/2;
  }
  return 1;
}

void emptyBuf(void) {
  while(getchar()!='\n');
  return;
}

int main(void) {
  int **W;
  int N;
  int power = 1;
  int i,j,k,l,p=0;
  while(1==1) {
    printf("enter the size of the matrix - must be a positive power of 2\n");
    if(scanf("%d", &N)!=1) {
      printf("unable to scan input\n"); 
      emptyBuf(); 
      continue;
    }
    if (!isPow2(N)) {
      printf("%d is not a valid power of 2\n", N); 
      continue;
    }
    break; // valid input: go on
  }

  W = twoDmatrix(N,N); // allocate memory for 2D matrix
  W[0][0]=1;   // this is the 1x1 Walsh code...

  while (power < N) {
    for(i=0; i<2; i++) {
      for(j=0; j<2; j++) {
        if (!(i==0 && j==0)) {
          for(k=0; k<power; k++) {
            for(l=0; l<power; l++) {
              if (i==1 && j == 1) {
                W[i*power+k][j*power+l] = -W[k][l]; // invert signal
              }
              else {
                W[i*power+k][j*power+l] = W[k][l]; // copy signal
              }
            }
          }
        }
      }
    }
    power *=2; // double matrix and repeat
  }

  // print out result
  for(i=0; i<N; i++) {
    for(j=0; j<N; j++) {
      printf("%2d ", W[i][j]);  // <<<<< updated
    }
    printf("\n");
  }
  free2D(W); // always remember to free your memory...
}
作为参考,请参阅-我从中得出以下结论:

POSTSCRIPT

关于
twoDmatrix()的一个注记
函数。我编写这个函数是因为没有直接的方法在C中分配一个大小未知的2D矩阵。所以这个函数创建一个指向
int
的指针数组-矩阵中的每一行一个指针;它还分配一个内存块-数组中的每个元素一个。然后它将一个指针与开始的o相关联f矩阵中的每一行,以便您可以使用通常的
W[i][j]
索引访问元素。这使得数组的第一行看起来非常长(它指向整个NxN块),第二行稍短一些,等等。但这只是一个技巧,因此您可以使用常用语法访问数组的元素。假设您有一个3x3数组,其中填充了数字0到8,然后情况如下所示:

pointer      values
W[0]         0 1 2
W[1]         3 4 5
W[2]         6 7 8
但另一种看法是:

0 1 2 3 4 5 6 7 8 
^ W[0]
      ^W[1]
            ^W[2]
这意味着您可以访问元素
W[0][6]
——它的值将与
W[1][3]
相同,这同样与
W[2][0]
相同

当您不再需要该函数时,必须释放两块内存—首先是数据块,然后是指针块。这就是free2D()函数的作用。

修改了您的代码。:我做了三件事:

1)使用更多块格式化
{…}
以提高可读性
2)使用
memset()为所有元素初始化数组
a[100][100]

3)添加了一个额外的
getchar()
(我的系统使用它而不是
getch()
),并注释了
clrsc()

它运行了4x4和8x8(但输出看起来不正确,您还有更多的工作要做):

main()
{
/*程序变量
维度变量,n
循环变量i,j
沃尔什表a的二维数组[100][100]*/
int n,j,i,a[100][100];
//clrsc();
//显示沃尔什表的用户输入
memset(a,0,100*100);
printf(“输入尺寸”);
scanf(“%d”和“&n”);
//将行从0迭代到“n”

对于(i=0;i请更具体地说明什么不符合要求。错误是什么???我的代码应该可以生成nxn沃尔什矩阵,但算法只能工作到4x4矩阵,我需要一些关于算法的帮助。(此代码本身没有错误。)我已经更新了我的代码,使其以您要求的形式生成输出。非常感谢。非常有帮助。我将对其进行修改,以将维度作为输入。谢谢。@Floris-如果我可以再次单击您,我会的。关于C多维矩阵的解释非常好。我将删除所有其他注释。@Ryker-没有我们感兴趣的交换,我将我不可能成为这个答案。所以谢谢你!
pointer      values
W[0]         0 1 2
W[1]         3 4 5
W[2]         6 7 8
0 1 2 3 4 5 6 7 8 
^ W[0]
      ^W[1]
            ^W[2]
main()
{

    /* Program variables
    Dimension variable, n
    Loop variables i,j
    Two dimensional array for walsh table a[100][100] */

      int n,j,i,a[100][100];
      //clrscr();
      // User input to display walsh table

      memset(a, 0, 100*100);
      printf("enter the size ");
      scanf("%d",&n);

      // Iterate rows from 0 to 'n'
      for(i=0;i<n;i++)
      {

      // Iterate columns from 0 to 'n' for each row 'i'
            for(j=0;j<n;j++)
            {
                if(i%2==1 && j%2==1) // for both i & j not divisible by 2, initialize array elements with -1
                {
                        a[i][j] = -1;
                }
                else if(i/2==1 && j/2==1)
                {  // for both i & j, if completely divisble by 2 and dividend is 1
                    if(j == 3 && i == 3)
                    {
                        a[i][j]=1;
                    }
                }
                else
                {
                        a[i][j] = -1;
                }
            }
            a[i][j] = 1;        // default case initialized to 1
      }
      a[3][3] = 1;

      // Output complete walsh table
      for(i=0;i<n;i++)
      {
          for(j=0;j<n;j++)
          {
          printf("\t%d",a[i][j]);
          }
          // go to next line after every row 
          printf("\n");
      }
      getchar();
      getchar();
}