【问题标题】:Please Explain the Output?请解释输出?
【发布时间】:2011-09-19 21:46:39
【问题描述】:

谁能解释一下程序的strage输出我知道该值与存储在数组中的值无关,而是与指针有关,但是第二个值如何变为5:

int main()
{
    int **h;
    int a[2][2]={1,2,3,4};
    h=(int **)a;
    int i,j;
    printf("%d",*h);
    (*h)++;
    printf("\n%d",*h);

    getch();
    return 0;
}

【问题讨论】:

  • 不提供链接,请在此处发布代码示例。
  • @Ed S. 一般来说,我讨厌 pastebins,但老实说...... ideone 很棒。这比仅在问题中发布代码要好得多 - 您可以看到编译器警告和输出。可惜它没有像 imgur 那样集成到 SO 中。
  • int a[2][2]={1,2,3,4}; 是如何编译的?
  • TBH,它不应该被标记为c++...
  • @AnkitSablok:但它仍然是 C 代码,所以 C++ 标记不应该存在。

标签: c


【解决方案1】:

发生的事情是*hint* 类型,它是一个指针。

当你增加时,它实际上会增加 4 而不是 1。因此你最后打印出来的数字是1 + 4 = 5

这是你的代码,有更多的打印:

  int **h; 
  int a[2][2]={1,2,3,4}; 
  h=(int **)a; 

  cout << h[0] << endl;
  cout << h[1] << endl;
  cout << h[2] << endl;
  cout << h[3] << endl;

  int i,j; 
  printf("%d",*h); 
  (*h)++; 
  printf("\n%d",*h); 

  cout << endl;
  cout << h[0] << endl;
  cout << h[1] << endl;
  cout << h[2] << endl;
  cout << h[3] << endl;

输出是:

00000001
00000002
00000003
00000004
1
5
00000005
00000002
00000003
00000004

所以你可以看到第一个值,增加了 4。因为 4 是编译为 32 位时指针的大小。

【讨论】:

  • 这个片段做了什么 int a[2][2]={1,2,3,4};
  • 还有 h[0] 等等,比如 h[4] 都将是 (int *),所以当你尝试打印它们时,y 是打印 1,2,3,4 的代码
  • 在这种情况下,它将a的前16个字节初始化为{1, 2, 3, 4}。老实说,我不知道你能做到这一点,所以它可能是未定义的行为。有人想添加到这里吗?
  • 你在这里所做的并不完全安全。但是当您执行h=(int **)a; 时,您将指针h 设置为指向数组的开头{1,2,3,4}。但是*h 是一个指针数组,因此您的值{1,2,3,4} 被解释为指针。因此,当您增加其中一个时,它们将增加 4。
【解决方案2】:

由于表达式*h 是一个指针 类型,指针算术开始发挥作用。请记住,指针算术考虑了基类型的大小;对于T *p 类型的任何指针,表达式p++ 将使指针p 前进sizeof T 字节。

由于*h 是一个初始化为值1 的指针,表达式(*h)++ 被读作“将sizeof (int *) 字节添加到1”,在您的情况下显然是4。因此输出为5。

【讨论】:

    【解决方案3】:

    通过h=(int **)a; 语句,您仅将数组a 的内存地址(第一个)分配给h。您还将 h 定义为 指向指针的指针,它也可以像您所做的那样指向二维数组。另外,可以看出,您没有将h 设为二维数组(递归使用malloc)。通过printf("%d",*h);,您正在尝试访问存储在h 中的地址处的值。

    数组以两种方式将值存储在内存中,按列或按行。无论哪种方式,内存位置都是连续的,在您的情况下也是如此。所以,h 存储了数组a 的第一个元素的内存地址。因此,当您使用*h 时,它会检索存储在h 中的地址处的值,即数组a 中的第一个值。当您将*h 递增(*h)++ 时,它会递增,因为*h 仍然是一个指针,并且正如您所知,递增指针并不意味着递增1,它实际上递增4

    因此,您将获得上述输出。

    欢迎您进一步讨论Ankit

    -沙普

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2014-09-24
      • 2023-03-24
      • 2015-07-13
      • 2012-02-21
      • 2015-03-28
      • 2013-10-09
      • 1970-01-01
      相关资源
      最近更新 更多