先决条件: Go 中的指针和将指针传递给函数
Go 编程语言或 Golang 中的指针是一个变量,用于存储另一个变量的内存地址。我们可以传递指向函数的指针,也可以从 Golang 中的函数返回指针。在 C/C++ 中,不建议在函数外返回局部变量的地址,因为它在函数返回后超出范围。因此,要在 C/C++ 中执行从函数返回指针的概念,您必须将局部变量定义为静态变量。
示例:在下面的程序中,代码行( int lv = n1 * n1; )将发出警告,因为它是函数的局部变量。为避免警告,将其设为静态。
// C++ program to return the
// pointer from a function
#include
using namespace std;
// taking a function having
// pointer as return type
int* rpf(int);
int main()
{
int n = 745;
// displaying the value of n
cout << n << endl;
// calling the function
cout << *rpf(n) << endl;
}
// defining function
int* rpf(int n1)
{
// taking a local variable
// inside the function
int lv = n1 * n1;
// remove comment or make the above
// declaration as static which
// result into successful
// compilation
// static int lv = n1 * n1;
// this will give warning as we
// are returning the address of
// the local variable
return &lv;
}
警告
prog.cpp: In function ‘int* rpf(int)’:
prog.cpp:24:9: warning: address of local variable ‘lv’ returned [-Wreturn-local-addr]
int lv = n1 * n1;
输出:
745
这种情况背后的主要原因是编译器总是为函数调用创建一个堆栈。一旦函数退出,函数堆栈也会被删除,这会导致函数的局部变量超出范围。将其设为静态将解决问题。由于静态变量具有即使在它们超出其作用域后仍保留其值的属性。
但是Go 编译器非常智能! .它不会将堆栈上的内存分配给函数的局部变量。它将在堆上分配这个变量。在下面的程序中,变量lv将在堆上分配内存,因为 Go 编译器将执行转义分析以将变量从本地范围中转义。
例子:
// Go program to return the
// pointer from the function
package main
import "fmt"
// main function
func main() {
// calling the function
n := rpf()
// displaying the value
fmt.Println("Value of n is: ", *n)
}
// defining function having integer
// pointer as return type
func rpf() *int {
// taking a local variable
// inside the function
// using short declaration
// operator
lv := 100
// returning the address of lv
return &lv
}
输出:
Value of n is: 100
注意: Golang 不支持像 C/C++ 那样的指针运算。如果您将执行,那么编译器将作为无效操作抛出错误。