* .cppファイルに静的クラスメンバー関数を実装する方法


125

staticヘッダーファイルではなく* .cppファイルにクラスメンバー関数を実装することは可能ですか?

すべてのstatic機能は常にinlineですか?


4
静的クラスメンバー関数をcppファイルに実装できない理由を説明できますか?エラー?通常、そのような関数を実装する場所についての制限はありません。
winterTTr 2011年

7
@ winterTTr、Web上のほとんどの例/チュートリアルが個別の実装例を示しておらず、代わりにヘッダーで宣言および定義しているため、おそらく質問が発生しました。少なくとも私のお気に入りの「C ++静的メンバー関数」の検索エンジンの最初の6ヒットはすべてこのようにしており、初心者が別のファイルにそれを実装する方法を説明していません。
クロバー2014年

7
実装するときは、staticキーワードを繰り返さないでください。staticヘッダーファイルのクラス定義にのみキーワードを書き込む
SomethingSomething

@crobar、あなたはマルチファイルの例が不足していることは正しいです。私は次のことを共有することを決めたので、私は、このアウトを理解するために苦労:
ドン・マクラクラン

回答:


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 ++が静的関数を処理する方法の詳細については、次のWebサイトをご覧ください


2

はい、*。cppファイルで静的メンバー関数を定義できます。ヘッダーで定義すると、コンパイラーはデフォルトでインラインとして扱います。ただし、静的メンバー関数の個別のコピーが実行可能ファイルに存在することを意味するものではありません。詳細については、この投稿に従ってください: C ++の静的メンバー関数は複数の翻訳単位でコピーされますか?


クラス本体で定義すると、自動的にデフォルトになります。それはクラス本体の外側ヘッダになら、それはより良いのいずれかにマークされていたinlineか、templateまたはあなたがリンカから複数の定義のエラーを取得します。
ベン・フォイト

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キーワードを使用しないようにしてください。

幸運を


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ディレクティブは、文字通り「このスポットに、そのファイル内のすべてのデータをコピーする」を意味します。したがって、ヘッダーファイルをインクルードすると、それはテキストファイル内のコードファイル内にあり、コードファイル(現在はコンパイルユニットまたは変換ユニットと呼ばれます)がプリプロセッサモジュールからコンパイラモジュールに渡されます。

つまり、静的メンバー関数の宣言と定義は、実際にはずっと同じファイルにありました...

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.