C++动态数组分配与MMSET的奇怪用法

C++动态数组分配与MMSET的奇怪用法,c++,pointers,C++,Pointers,我最近在C++中遇到了这段代码: int m=5; int n=4; int *realfoo = new int[m+n+3]; int *foo; foo = realfoo + n + 1; memset(realfoo, -1, (m+n+2)*sizeof(int)); 代码的其余部分只使用变量foo,而realfoo永远不会被使用,只是在最后被释放。 我不明白那是什么意思。 什么样的操作是foo=realfoo+n+1;?如何分配一个数组加上一个int? memset将realfo

我最近在C++中遇到了这段代码:

int m=5;
int n=4;
int *realfoo = new int[m+n+3];
int *foo;
foo = realfoo + n + 1;
memset(realfoo, -1, (m+n+2)*sizeof(int));
代码的其余部分只使用变量foo,而realfoo永远不会被使用,只是在最后被释放。 我不明白那是什么意思。 什么样的操作是foo=realfoo+n+1;?如何分配一个数组加上一个int? memset将realfoo的每个值都设置为-1。这对foo有什么影响

编辑 因为很多人都要求完整的代码。这是:

int Wu_Alg(char *A, char *B, int m, int n)
{
   int *realfp = new int[m+n+3];
   int *fp, p, delta;
   fp = realfp + n + 1;
   memset(realfp, -1, (m+n+2)*sizeof(int));
   delta = n - m;
   p = -1;
   
   while(fp[delta] != n){
      p=p+1;
      for(int k = -p; k <= delta-1; k++){
         fp[k]=snake(A, B, m, n, k, Max(fp[k-1]+1, fp[k+1]));          
      }
      for(int k = delta+p; k >= delta+1; k--){
         fp[k] = snake(A, B, m, n, k, Max(fp[k-1]+1, fp[k+1]));        
      }
      fp[delta] = snake(A, B, m, n, delta, Max(fp[delta-1]+1, fp[delta+1]));
   }
   delete [] realfp;
   return delta+2*p;
}
int snake(char *A, char *B, int m, int n, int k, int j)
{
   int i=j-k;
   while(i < m && j < n && A[i+1] == B[j+1]){
      i++;
      j++;
   }
   return j;
}
资料来源: 算法是:

这个:

foo = realfoo + n + 1;
指定foo指向realfoo的元素n+1。使用数组索引/指针算术等价性,它与:

foo = &realfoo[n + 1];
这:

指定foo指向realfoo的元素n+1。使用数组索引/指针算术等价性,它与:

foo = &realfoo[n + 1];
memset没有将值设置为-1。它用于将每个字节转换为-1 您应该创建一个循环来迭代每个元素以正确分配

for(size_t i= 0; i< m+n+3; i++){
    realfoo[i] = -1;
}
memset没有将值设置为-1。它用于将每个字节转换为-1 您应该创建一个循环来迭代每个元素以正确分配

for(size_t i= 0; i< m+n+3; i++){
    realfoo[i] = -1;
}
什么样的操作是foo=realfoo+n+1

这是一个赋值操作。将为左侧操作数变量foo分配一个新值。右侧操作数realfoo+n+1提供该值

如何分配一个数组加上一个int

因为数组衰减为指针

memset将realfoo的每个值都设置为-1

不完全是。设置了除最后一个值之外的所有值。最后一个未初始化

请注意,从技术上讲,每个字节都设置为-1。如果系统使用有符号整数的补码表示,则结果整数的值将不是-1,假设为32位整数和8位字节,则结果整数的值将是-16'843'009

这对foo有什么影响

foo本身不受影响。但是foo指向一个受影响的对象

额外建议:示例程序泄漏内存。我建议避免拥有裸指针

什么样的操作是foo=realfoo+n+1

这是一个赋值操作。将为左侧操作数变量foo分配一个新值。右侧操作数realfoo+n+1提供该值

如何分配一个数组加上一个int

因为数组衰减为指针

memset将realfoo的每个值都设置为-1

不完全是。设置了除最后一个值之外的所有值。最后一个未初始化

请注意,从技术上讲,每个字节都设置为-1。如果系统使用有符号整数的补码表示,则结果整数的值将不是-1,假设为32位整数和8位字节,则结果整数的值将是-16'843'009

这对foo有什么影响

foo本身不受影响。但是foo指向一个受影响的对象


额外建议:示例程序泄漏内存。我建议不要拥有裸指针。

新的不是C的一部分,你必须使用C++它们不是数组,它们是指针-你正在改变指针foo指向的对象,现在foo指向realfoo数组的中间。这没什么错。有时,如果你想使用负指数,这很方便:foo[-n-1]、foo[-n]、…、foo[-1]、foo[0]、foo[1]、…、foo[m+1]都是有效的。如果不看,就无法给出任何理由。代码可能会使用块中的前5个int作为某种类型的元数据(谁知道呢),但我们可以通过MCVE判断……foo=realfoo+n+1相当于foo=&realfoo[n+1]。因此,它将realfoo视为一个数组,并使foo指向其n+1个元素。这意味着foo[i]是realfoo[i+n+1]的别名。这也意味着foo可以具有负索引,例如foo[-n-1]是别名realfoo[0]。奇怪的是,memset调用设置了realfoo的m+n+2元素,并使realfoo[m+n+2]未初始化,这是分配块的一部分-结果是,如果realfoo[m+n+2]未初始化,则访问其值会给出未定义的行为。new不是C的一部分,您必须使用C++它们不是数组,它们是指针-您正在更改指针foo指向的对象,现在foo指向realfoo数组的中间。这没什么错。有时,如果你想使用负指数,这很方便:foo[-n-1]、foo[-n]、…、foo[-1]、foo[0]、foo[1]、…、foo[m+1]都是有效的。如果不看,就无法给出任何理由。代码可能会使用块中的前5个int作为某种类型的元数据(谁知道呢),但我们可以通过MCVE判断……foo=realfoo+n+1相当于foo=&realfoo[n+1]。因此,它将realfoo视为一个数组,并使foo指向其n+1个元素。这意味着foo[i]是realfoo[i+n+1]的别名。这也意味着foo可以具有负索引,例如foo[-n-1]是别名realfoo[0]。奇怪的是,memset调用设置了realfoo的m+n+2元素,并使realfoo[m+n+2]处于未初始化状态,它是已分配块的一部分
已初始化-结果是,如果realfoo[m+n+2]未初始化,则访问其值会产生未定义的行为。你的确切意思是什么?这种方法也会初始化,为什么要在memset上使用它?@costaparas:memset方法依赖于这样一种假设,即int-1在内部表示为-1的重复字节,这并不能保证在所有平台上都是正确的,尽管在许多常见的平台上都是正确的。@nate Thanke忘记了这一点,通常memset用于char数组而不是int数组。但是由于这是C++而不是C,所以STD::FILIN将是首选的方法。你到底是什么意思?这个方法也初始化了,为什么使用这个在MeMSET?@ COSTARPAS:MeMeSET方法依赖于假设INT 1在内部被表示为重复的字节1。这并不能保证在所有平台上都是正确的,尽管在许多常见的平台上都是正确的。@nate Thanke忘记了这一点,通常memset用于char数组而不是int数组。但是由于这是C++而不是C,所以STD::FILIN将是首选方法。