【问题标题】:How to increment a dereferenced double pointer?如何增加取消引用的双指针?
【发布时间】:2013-01-09 15:09:32
【问题描述】:

在我通常会使用的代码中:

#include <stdlib.h>

void dref1(char **blah)
{
    (*blah)[0] = 'a';
    (*blah)[1] = 'z';
    (*blah)[2] = 0x00;
}

/* or */

void dref2(char **blah)
{
    char *p = *blah;

    *p++ = 'w';
    *p++ = 't';
    *p = 0x00;
}


int main(void)
{
    char *buf = malloc(3);

    dref1(&buf);
    puts(buf);
    dref2(&buf);
    puts(buf);
    free(buf);

    return 0;
}

我的问题是是否有可能/如何直接取消引用和增加指针:

**blah = 'q';       /* OK as (*blah)[0] ? */
(*blah)++;          /* Why not this? */
*((*blah)++) = 'w'; /* ;or. */
...

【问题讨论】:

    标签: c pointers dereference


    【解决方案1】:

    我认为dref1 没有任何问题。

    (*blah)[0] = *(*blah)+0 = **blah

    所以你可以写(*blah)[0]='a';

    (*blah)++; 没有意义,您只是在增加和丢失malloc 返回的地址。

    【讨论】:

      【解决方案2】:

      是的,我们可以。只测试一窝。我想你有这个想法。

      使用blah 编写的问题在于,当您返回主程序时,不仅缓冲区的内容发生了变化(如您所愿),而且指针buf 本身也发生了变化。这可能不是你想要的,也绝对不是你需要释放的。

      测试:

      #include <stdlib.h>
      
      void dref1(char **blah)
      {
          (*blah)[0] = 'a';
          (*blah)[1] = 'z';
          (*blah)[2] = 0x00;
      }
      
      /* or */
      
      void dref2(char **blah)
      {
          char *p = *blah;
      
          *p++ = 'w';
          *p++ = 't';
          *p = 0x00;
      }
      
      void dref3(char **blah)
      {
          *(*blah)++ = 'w';
          *(*blah)++ = 't';
          *(*blah) = 0x00;
      }
      
      void dref4(char **blah)
      {
          **blah = 'q';       /* OK as (*blah)[0] ? */
          (*blah)++;          /* Why not this? */
          *((*blah)++) = 'w'; /* ;or. */
      
      }
      
      
      int main(void)
      {
          char *buf = (char*)malloc(3);
          char *buf1=buf;
          dref1(&buf);
          puts(buf);
          dref2(&buf);
          puts(buf);
          dref3(&buf);
          puts(buf);
          puts(buf1);
      
          buf=buf1;
          dref4(&buf);
          puts(buf);
          puts(buf1);
      
          free(buf1);
      
          return 0;
      } 
      

      【讨论】:

      • 是的。谢谢。我自己才意识到:)。这就是问题所在。一旦我意识到自己在做什么,就非常明显了。
      • 测试一下什么,伙计?
      【解决方案3】:

      我不知道你的真正意图是什么,但在我看来,你需要了解 *p++(*p)++ 作为表达式之间的区别。

      第一个表达式取消引用指针并推进指针本身,而不是指向的值。

      第二个表达式取消引用指针并通过应用后缀++ 运算符修改指向的值。指向的值是指针还是整数都无关紧要。

      这与一元 * 运算符和后缀 ++ 运算符的优先级有关。在没有括号的情况下,首先应用++ 运算符,并将其结果用作* 运算符的操作数。

      编辑:

      假设blahchar ** 类型,这里列出了可能的操作以及每个操作的操作:

      • 显然,blah 产生一个 char ** 类型的值;
      • *blah 产生 char *;
      • **blah 产生 char;
      • *(*blah)++ 取消引用 blah 得到 char *,然后 *p++ 类比来了。
      • **blah++ 取消引用 blah 两次以获取指向的值,然后递增 blah 指针。
      • (**blah)++ 两次取消引用 blah 指针,然后 (*p)++ 类比来了。

      【讨论】:

      • 注意**blah++增加了buf的地址,在这种情况下是堆栈地址,在下一条语句中为blah赋值可能会导致堆栈崩溃。
      猜你喜欢
      • 1970-01-01
      • 2014-11-03
      • 2012-12-31
      • 2012-01-04
      • 2010-10-25
      • 2021-12-30
      • 1970-01-01
      • 2020-03-17
      相关资源
      最近更新 更多