如何在* .cpp文件中实现静态类成员函数?


125

是否可以static在* .cpp文件中实现类成员函数,而不是在头文件中实现它?

所有static功能都总是inline吗?


4
您能解释一下为什么您无法“实现” cpp文件中的静态类成员功能吗?有什么错误吗?关于在何处实现此类功能通常没有限制。
winterTTr 2011年

7
@winterTTr,可能会出现此问题,因为网络上的大多数示例/教程并未提供单独的实现示例,而是在标头中声明和定义了该示例。至少在我最喜欢的“ C ++静态成员函数”搜索引擎中,前六个命中都是这样做的,并且没有为新手解释如何在单独的文件中实现它。
crobar 2014年

7
实施时,请勿重复该static关键字。static仅在头文件的类定义中写入关键字
SomethingSomething

@crobar,很正确,因为缺少多文件示例。我很难弄清楚这一点,因此决定分享以下内容:
Don Mclachlan

Answers:


153

它是。

test.hpp:

class A {
public:
    static int a(int i);
};

test.cpp:

#include <iostream>
#include "test.hpp"


int A::a(int i) {
    return i + 2;
}

using namespace std;
int main() {
    cout << A::a(4) << endl;
}

它们并不总是内联的,不,但是编译器可以使它们内联。


47

试试这个:

header.hxx:

class CFoo
{
public: 
    static bool IsThisThingOn();
};

class.cxx:

#include "header.hxx"
bool CFoo::IsThisThingOn() // note: no static keyword here
{
    return true;
}

9

helper.hxx

class helper
{
 public: 
   static void fn1 () 
   { /* defined in header itself */ }

   /* fn2 defined in src file helper.cxx */
   static void fn2(); 
};

helper.cxx

#include "helper.hxx"
void helper::fn2()
{
  /* fn2 defined in helper.cxx */
  /* do something */
}

A.cxx

#include "helper.hxx"
A::foo() {
  helper::fn1(); 
  helper::fn2();
}

要了解有关c ++如何处理静态函数的更多信息,请访问:c ++中的静态成员函数是否在多个转换单元中复制?


2

是的,您可以在* .cpp文件中定义静态成员函数。如果您在标头中定义它,则编译器默认会将其视为内联。但是,这并不意味着静态成员函数的单独副本将存在于可执行文件中。请按照这篇文章了解更多信息: c ++中的静态成员函数是否以多个翻译单元复制?


如果您在类主体中定义它,它将自动为默认值。如果它位于类主体之外的标头中,则最好将其标记为inline或,template否则您将从链接程序中收到多个定义错误。
Ben Voigt

2

在头文件中说foo.h

class Foo{
    public:
        static void someFunction(params..);
    // other stuff
}

在您的实现文件中说foo.cpp

#include "foo.h"

void Foo::someFunction(params..){
    // Implementation of someFunction
}

很重要

只需确保在实现文件中实现static函数时,不要在方法签名中使用static关键字即可。

祝好运


1

@crobar,您确实对多文件示例不多了,所以我决定分享以下内容,希望对其他人有所帮助:

::::::::::::::
main.cpp
::::::::::::::

#include <iostream>

#include "UseSomething.h"
#include "Something.h"

int main()
{
    UseSomething y;
    std::cout << y.getValue() << '\n';
}

::::::::::::::
Something.h
::::::::::::::

#ifndef SOMETHING_H_
#define SOMETHING_H_

class Something
{
private:
    static int s_value;
public:
    static int getValue() { return s_value; } // static member function
};
#endif

::::::::::::::
Something.cpp
::::::::::::::

#include "Something.h"

int Something::s_value = 1; // initializer

::::::::::::::
UseSomething.h
::::::::::::::

#ifndef USESOMETHING_H_
#define USESOMETHING_H_

class UseSomething
{
public:
    int getValue();
};

#endif

::::::::::::::
UseSomething.cpp
::::::::::::::

#include "UseSomething.h"
#include "Something.h"

int UseSomething::getValue()
{
    return(Something::getValue());
}


0

#include指令的字面意思是“将文件中的所有数据复制到此位置”。因此,当您包含头文件时,它以文本形式位于代码文件中,并且当代码文件(现在称为编译单元翻译单元)位于从预处理器模块移交给编译器模块。

这意味着您的静态成员函数的声明和定义实际上一直在同一文件中...

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.