返回介绍

1. 定义

发布于 2024-10-12 21:58:08 字数 2638 浏览 0 评论 0 收藏 0

函数是指令组织和最小重用单元,完成一个相对独立的任务。

每个函数仅被定义一次,但可在多处声明。函数被调用前,必须先声明(前置声明)。声明中的参数名可选。实际上对编译器没有意义,只是可增加使用者友好度。

  • 函数不是第一类对象(first-class)。
  • 不支持重载(overload)。
  • 不支持默认参数。
  • 不支持多返回值。
  • 不支持嵌套。(ISO C 不支持,GCC 扩展支持)
  • 不支持匿名函数,不支持闭包。
return_type func_name(params) 
{
	code block
}

修饰符

  • extern : 默认。外链接,其他模块可用。
  • static : 内链接,仅当前模块可用。
  • inline : 和 static 配合,建议编译器内联。(用于定义)
  • _Noreturn : 告知编译器,该函数不再返回。

_Noreturn 表示调用该函数后不再返回调用处,编译器会优化掉后续代码。

如果该函数没有执行流终止行为(比如 exitlongjmp ),则编译器会警告。

_Noreturn static void test ()
{
    exit(0);
}

int main (void) 
{
    test();

    // 不再生成后续指令。
    printf("hello, world!\n");  
    
    return 0;
}

参数

使用逗号分隔多个参数。如没有参数,可为空或 void。不能合并多个相同类型的参数。

int add (int x, y)
{               ^ unknown type name 'y'

参数被当做函数局部变量对待。可使用 register 声明,但可能被编译器忽略。

参数总是值传递。可通过复制指针传递引用,或用二级指针实现传出参数(out)。

位于函数参数列表里的称作形参( parameter ),传递给函数调用的称作实参( argument )。

形参在调用时分配存储空间,其作用域为函数块;实参会被复制成形参,它可以是变量、常量或表达式。

所以,默认对形参的修改不影响实参。(注意区别指针间接修改)

void test (int **x) 
{
    int *p = malloc(sizeof(int));
    *p = 100;
    *x = p;
}

int main (void) 
{
    int x = 10;
    int *p = &x;
    printf("%p\n", p);

    test(&p);
    printf("%p\n", p);
    free((void*)p);

    return 0;
}

虽然生成代码相同,但 func() 表示未指定参数数量和类型, func(void) 则明确表示没有参数。

void test() 
{
    test(100);
    return;
}

如参数列表是 test() ,代码可编译,编译器不会检查调用参数是否正确。

test(void) ,会明确引发一个编译错误。

数组类型参数方括号内常量表达式实际会被忽略。

但使用 type[] 要比 type* 更明确表明要接收一个数组,而不仅仅是个指针。

虽然两者行为相同,但对于使用者更友好。

void test (int x[8])
{
    printf("%p\n", x);
}

int main (void) 
{
    test((int[3]){1, 2, 3});
    return 0;
}

返回值

返回值可以是 void,或函数和数组之外的其他类型。

可返回堆内存指针(malloc),返回函数和数组指针。

typedef int data_t[3];

data_t test () 
       ^~~~ error: 'test' declared as function returning an array
{
typedef void (func_t)();

func_t test ()
       ^~~~ error: 'test' declared as function returning a function
{

返回局部变量指针存在风险。

int* test ()
{
    int x = 100;
    return &x;
           ^~ warning: function returns address of local variable
}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据
    我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
    原文