【问题标题】:How a double pointer fetch the value from a single poiner双指针如何从单个指针中获取值
【发布时间】:2021-01-07 00:35:43
【问题描述】:

一个数组现在由一个指针指向。双指针指向单指针。我正在尝试使用此双指针获取数组的值。到目前为止,我只通过 双指针 获取了数组的第一个索引值。 我知道如果我取消引用 (*ptr2) 双指针,那么它将给出第一个指针指向的地址 (ptr1),这意味着数组的第一个索引地址 (&array[0])。

#include <iostream>
using namespace std;

int main(){
    int array[5]{15,25,35,45,55};
    int* ptr1;
    int** ptr2;

    ptr1 = &array[0];
    ptr2 = &ptr1;

在下面的 for 循环中,我尝试使用指针 ptr1 打印 array 的值。

    for(int i =0; i<5; i++){
        cout<<"the value: "<<*(ptr1+i)<<" lives at "<<ptr1+i<<" address\n";
    }
    cout<<"\n";

在下面的 for 循环中,我尝试检查 *ptr2 是否一直给我 ptr1 指向的地址。但我发现它只对第一个索引有效/相同,然后它是 (*ptr2) 给我一个不同的地址

    for(int j=0; j<5; j++){
        cout<<"adress of array: "<<&array[j]<<" , ptr1: "<<(ptr1+j)<<" , val of ptr2: "<<*(ptr2+j)<<endl;
    }

    cout<<"\n";
    return 0;
}

虽然我尝试使用 **ptr2+i 使用 for 循环从 ptr2 获取值,但它只持续了 2 次。第一次正确的值很明显,因为我看到array[0]*(ptr2+0) 的地址相同。第二次垃圾值,然后 Segmentation fault (core dumped)

我想到了一个猜测,ptr1ptr2 都是 int 类型,但一个指向变量,另一个指向指针。所以也许从一开始就出现了一个内存分配的概念,我被跳过了。

有什么方法可以使用上述结构获取数组的值?

【问题讨论】:

    标签: c++ pointers double-pointer


    【解决方案1】:

    ptr2 指向ptr1(ptr2+j),当 j 不是 0 时,是您尚未分配的地址,因此取消引用它 (*(ptr2+j)) 会使您的程序具有 undefined behavior 并获得 分段错误一种可能的结果。

    您应该首先取消引用它,然后索引:(*ptr2)[j]*((*ptr2)+j),如果您愿意的话。

    【讨论】:

      【解决方案2】:

      你的推理很接近,但你没有很好地应用它。

      我知道如果我取消引用 (*ptr2) 一个双指针,那么它将给出第一个指针指向的地址 (ptr1)

      换句话说,*ptr2ptr1 的同义词。因此,您看到ptr1 的任何地方(在分配ptr2 = &amp;ptr1 之后)都可以替换为*ptr2。更好的是,替换为(*ptr2) 以避免来自优先级高于取消引用的运算符的干扰。举个例子:

         for(int i =0; i<5; i++){
             cout<<"the value: "<<*(ptr1+i)<<" lives at "<<ptr1+i<<" address\n";
         }
         cout<<"\n";
      

      现在做一个简单的查找和替换。将ptr1 替换为(*ptr2)。不要试图调整任何东西;一旦你决定这样做,这个过程就是无意识的。

          for(int i =0; i<5; i++){
              cout<<"the value: "<<*((*ptr2)+i)<<" lives at "<<(*ptr2)+i<<" address\n";
          }
          cout<<"\n";
      

      这几乎是您在循环中尝试的,除了您使用*(ptr2+j) 而不是(*ptr2)+i。我们可以忽略从ij 的变化,但这些括号很重要。您更改了操作顺序,这相当于使用3(1+4) 而不是(3×1)+415 在需要 7 的地方不起作用,同样在取消引用之前添加 j 在需要首先进行取消引用的地方也不起作用,这不足为奇。

      注意:由于取消引用的优先级高于添加,因此可以从此特定示例中删除 *ptr2 周围的括号。也就是说,*ptr2+i*(*ptr2+i) 也可以工作。

      注意:这个问题可以证明为什么避免使用指针通常是明智的。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2021-12-16
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2022-11-30
        相关资源
        最近更新 更多