谷歌关于输入/输出参数的样式指南作为指针

时间:2014-10-18 15:10:15

标签: c++ parameters reference google-style-guide cpplint

Google C++ Style Guide在输入参数(→const ref,value)和输入输出或输出参数(→非常量指针)之间明确区分(严格遵循cpplint.py):

  

C / C ++函数的参数是函数的输入,输出   从功能,或两者。输入参数通常是值或   const引用,而输出和输入/输出参数将是   非常量指针。

进一步说:

  

事实上,Google代码中的一个非常强大的惯例是输出参数是值或const引用,而输出参数是指针。

但我无法弄清楚为什么不应该通过引用传递输入/输出参数(我将输出参数放在一边)。在stackoverflow上有很多与此问题相关的主题:例如here,接受的答案清楚地说明了

  

主要是关于风格

但如果

  

你希望能够传递null,你必须使用指针

那么,如果我想避免指针为空,那么总是要求指针的重点是什么?为什么只使用输入参数的引用?

4 个答案:

答案 0 :(得分:26)

要求输出参数作为指针传递的原因很简单:

它清楚地表明在呼叫站点,该参数可能会发生变异:

foo(x, y);     // x and y won't be mutated
bar(x, &y);    // y may be mutated

当代码库发展并经历由可能不了解整个上下文的人员审核的增量更改时,能够尽快了解更改的上下文和影响非常重要。因此,使用此样式规则,可以立即清楚更改是否会引入变异。

答案 1 :(得分:6)

他们提出的观点(我不同意)就是说我有一些功能

void foo(int a, Bar* b);

如果b参数是可选的,或者有时不需要,你可以像这样调用函数

foo(5, nullptr);

如果函数声明为

void foo(int a, Bar& b);

然后 无法传递Bar

这一点(强调我的)完全是基于意见的,取决于开发人员的自由裁量权。

  

事实上,Google代码中的一个非常强大的惯例是输入参数是值或const引用,而输出参数是指针

如果我打算将b作为输出参数,则以下任何一种都是完全有效且合理的。

void foo(int a, Bar* b);  // The version Google suggests
void foo(int a, Bar& b);  // Reference version, also perfectly fine.

答案 2 :(得分:4)

你是第一个问题:“那么,如果我想避免指针为null总是要求指针有什么意义?”

使用指针向调用者宣告他们的变量可能被修改。如果我致电foo(bar)bar是否会被修改?如果我拨打foo(&bar),则可以修改bar的值 有许多函数的例子,其中null表示一个可选的输出参数(在我的头顶time是一个很好的例子。)

你的第二个问题:“为什么只使用输入参数的引用?”

使用引用参数比使用指针参数更容易。

int foo(const int* input){
    int return = *input;

    while(*input < 100){
        return *= *input;
        (*input)++;
    }
}

使用引用重写的代码如下所示:

int foo(const int& input){
    int return = input;

    while(input < 100){
        return *= input;
        input++;
    }
}

您可以看到使用const int& input简化了代码。

答案 3 :(得分:1)

他们可能会使用它来保持一致性,因为它们使用输出参数作为对现有内存的引用(它们修改以前初始化的变量)和实际输出(假设输出参数由函数本身分配)。为了保持一致性,他们将其用作更清楚地表明输入与输出的方法。

如果您从不需要函数/方法来分配输出参数的内存,例如从查找返回指针或分配内存本身并通过指针返回它,请使用引用。如果您需要这样做但不关心使用指针作为参数是输入还是输出的指示,请在适当时使用输出参数的引用。在所有情况下都没有绝对要求使用指针,除非该函数/方法本身的要求需要它。