从函数返回指针作为静态变量

时间:2016-03-02 14:03:32

标签: c arrays function pointers static

我正在学习C并阅读this

#include <stdio.h>
#include <time.h>

/* function to generate and retrun random numbers. */
int * getRandom( ) {

   static int  r[10];
   int i;

   /* set the seed */
   srand( (unsigned)time( NULL ) );

   for ( i = 0; i < 10; ++i) {
      r[i] = rand();
      printf("%d\n", r[i] );
   }

   return r;
}

/* main function to call above defined function */
int main () {

   /* a pointer to an int */
   int *p;
   int i;

   p = getRandom();

   for ( i = 0; i < 10; i++ ) {
      printf("*(p + [%d]) : %d\n", i, *(p + i) );
   }

   return 0;
}

文章解释说,由于函数中声明的指针是局部变量,因此必须将其定义为“静态”。 (第7行,变量r)

我关注的有三点。

  • 首先,“static int r [10]”声明他们想要创建一个大小为10的int数组。当它从getRandom函数返回“return r”时,该函数实际返回 r [10]的第一个成员的地址,或指针到r [10]的第一个地址?

  • 其次,在main函数中,p = getRandom()表示从getRandom()返回的地址或指针被赋值给指针p。尽管getRandom()一旦停止工作,r就会失效,地址就已经分配给了p。那么,为什么需要声明为静态?

    或getRandom()返回指向r [10]的指针的地址,因此当消失时,p会指向空地址而不是r [10]?

    或者,当getRandom()停止时,不仅指向r,而且r [10]数组也会消失,所以它需要是静态的吗?

  • 第三,是否正确,没有malloc声明的任何函数中的变量都会被存储为堆栈内存?

3 个答案:

答案 0 :(得分:1)

getRandom()返回指向r[10]的第一个元素的指针。

引自N1256 6.3.2.1左值,数组和函数指示符

  

3除非它是sizeof运算符或一元&amp;的操作数。运营商,或者是   用于初始化数组的字符串文字,类型为''数组类型'的表达式是   转换为类型为''指向类型'的指针的表达式,指向的初始元素   数组对象并不是左值。如果数组对象有寄存器存储类,则   行为未定义。

如果r[10]不是static,则数组将从getRandom()返回时消失,之后访问将调用未定义的行为

“没有malloc声明的任何函数中的变量将被存储为堆栈内存”不正确。 C中的任何变量都不需要存储为堆栈内存。通常,静态变量不存储在堆栈上,而具有自动存储持续时间的变量存储在堆栈中。

答案 1 :(得分:1)

  

该函数实际返回r [10]的第一个成员的地址,或指向r [10]的第一个地址的指针?

答:第一个成员的地址。

  

尽管getRandom()一旦停止工作,就会失败,......

答:不,static变量不会进入程序堆栈内存(与局部变量不同)。他们生活整个程序执行时间。

  

第三,是否正确,没有malloc声明的任何函数中的变量都会被存储为堆栈内存?

简而言之,是的。 OTOH,malloc() - 内存生存期不受函数范围的限制。

答案 2 :(得分:0)

  

文章解释说,因为在函数中声明的指针是a   局部变量,因此必须定义为静态&#39;。 (第7行,   变量r)

r是一个整数数组,而不是指针。而本地并不意味着static,这推断出另一种含义。

  

该函数实际返回第一个成员的地址   r [10],或指向r [10]的第一个地址的指针?

它会返回第一个成员的地址:当您键入return r时会自动发生这种情况,这相当于更详细的return &r[0]

static变量从程序开头就存在,并在其末尾被销毁 - 因此在main之前和main之后。要返回指向本地数据的指针,例如从函数返回,它必须是static,否则 - 如果你说 - 你将访问被解除分配的数据,这是不允许的。