ベストプラクティス:クラス定義内でのパブリック/保護/プライベートの順序付け?


92

私はゼロから新しいプロジェクトを始めており、それがクリーンである/良いコーディング標準を持っていることを望んでいます。ここのベテラン開発者は、クラス内でどのような順序でレイアウトを行いますか?

A:1)パブリックメソッド2)プライベートメソッド3)パブリック変数4)プライベート変数

B:1)パブリック変数2)プライベート変数3)パブリックメソッド4)プライベートメソッド

C:1)パブリック変数2)パブリックメソッド3)プライベートメソッド4)プライベート変数

私は一般にパブリック静的変数を一番上に置きたいのですが、パブリック静的メソッドをコンストラクターの前にリストするのでしょうか、それともコンストラクターを常に最初にリストする必要がありますか?そういうこと...

私はそれが微妙だと知っていますが、私はただ疑問に思いました:これのためのベストプラクティスは何ですか?

PS:いいえ、Cc#は使用しません。知っている。私はラディットです。


9
C#を使用しないことには何の問題もありません。私はプロの開発者として長年にわたってC#のステッチを書いたことはありません。タスクに適した言語を使用し、どこにでも行きたいところがあると言っている人にはそれを貼り付けてください。
エーテル、

回答:


141

きれいなコード、ロバートC.マーティンは、クラスの最上部に常に入れメンバ変数へのコーダー(最初の定数、そしてプライベートメンバー)を助言し、彼らは原因がない話のように読めるようにする方法は、Aの方法で発注する必要があり読者はコードをあちこち飛び回る必要がある。これは、アクセス修飾子ではなく、コードを整理するためのより賢明な方法です。


10
私は幸運にも追加しました:ゲッター/セッターは最後に。これは、クラスのかさばりを軽減するのに役立ちます。
Dean J

5
メンバー変数の直後の上部にあるコンストラクター。OOPでは、実行はオブジェクトのインスタンス化から始まります。
Asaph 2014年

6
読者にコードをあちこち飛び回らせてしまうのは、おそらく、読者にプライベートメソッドの細かいところまで詳細を読ませるのとバランスを取る必要があるでしょう。新聞のメタファーはおそらく、あなたのパブリックメソッドがクラスが行うことを広く表す必要があり、プライベートメソッドが詳細を提供するという点で誤解されています(必要に応じて参照できる脚注のように)。
Kenny Hung

1
よくわかりません。あなたは言った:(最初に定数、次にプライベートメンバー)。OK。それでは、公衆はどこへ行くのでしょうか?
ハニー

1
@ハニー彼らは定数とプライベートメンバーのすぐ後に行きます。つまり、定数、プライベートメンバー、パブリックメンバーの順になります。
ピエールジレット

48

ベストプラクティスは一貫性を保つことです。

個人的に、私は入れ好むpublic続く、最初の方法をprotectedして、次の、メソッドprivateの方法。メンバーデータは、そうであるという正当な理由がない限り、通常は常にプライベートまたは保護されている必要があります。

publicメソッドを一番上に置くことの私の理論的根拠は、それがクラスのインターフェースを定義するため、ヘッダーファイルを閲覧する人は誰でもこの情報をすぐに見ることができるはずです。

一般にprivateprotectedメンバーは、クラスの内部を変更することを検討していない限り、ヘッダーファイルを参照するほとんどの人にとってそれほど重要ではありません。それらを「邪魔にならないように」保持することにより、この情報が、カプセル化のより重要な側面の1つである、知る必要がある場合にのみ維持されることが保証されます。


LeopardSkikPBH、私は完全に同意します...それは理にかなっています!その中で、varまたはfuncsが優先されるかどうかについて、私は混乱していると思います。ありがとう!
tempname 2009年

10
ベストプラクティスが一貫していることには同意しません。読み取り不能で保守不可能なコードを一貫して書く方法はたくさんあります。
jason

3
@Jasonは、事故が発生する可能性があるため、道路脇にいるのはベストプラクティスではないと言っているようなものです。
レックスM

1
@ジェイソン-多分私はもっと明確だったはずです。特に、かなり主観的なケース(メソッドの順序付け)では、一貫性を保つことがベストプラクティスだと思います。誰もが物を注文する最良の方法について意見を持っていますが、あなたが本質的に一貫しているのであれば、それはかなり保守可能でなければなりません。特に一貫性のあるコードは、コードのすべての領域で常にベストプラクティスであるとは限らないことに同意します。
LeopardSkinPillBoxHat 2009年

3
@レックスM:いいえ、私が言ったことはあなたの解釈と全く似ていません。私の要点は、この場合、一貫しているだけでは強力な議論ではないということです。いくつかのケースでは一貫性は問題ありません(例えば、ブレースの配置)。しかし、ここでの選択は実際にはコードの可読性に影響を与えます。したがって、一貫性よりも強力な議論が必要です。
ジェイソン

8

私はこれに関して、他の哲学とは異なる哲学を持っていると思います。関連するアイテムをグループ化することを好みます。クラスで作業するためにジャンプする必要があるのが我慢できません。コードはフローする必要があり、アクセシビリティ(パブリック、プライベート、保護など)またはインスタンス対静的またはメンバー対プロパティ対関数に基づいてかなり人工的な順序を使用しても、適切なフローを維持できません。そのMethodため、プライベートヘルパーメソッドなどによって実装されるパブリックメソッドをナビゲートする場合HelperMethodAHelperMethodBこれらのメソッドをファイル内で互いに離すのではなく、それらを互いに近づけます。同様に、静的メソッドによって実装されるインスタンスメソッドがある場合は、これらもグループ化します。

したがって、私のクラスは次のようになります。

class MyClass {
    public string Method(int a) {
        return HelperMethodA(a) + HelperMethodB(this.SomeStringMember);
    }

    string HelperMethodA(int a) { // returns some string }

    string HelperMethodB(string s) { // returns some string }

    public bool Equals(MyClass other) { return MyClass.Equals(this, other); }

    public static bool Equals(MyClass left, MyClass right) { // return some bool }

    public double SomeCalculation(double x, double y) {
        if(x < 0) throw new ArgumentOutOfRangeException("x");
        return DoSomeCalculation(x, y); 
    }

    const double aConstant;
    const double anotherConstant;
    double DoSomeCalculation(double x, double y) {
        return Math.Pow(aConstant, x) * Math.Sin(y) 
            + this.SomeDoubleMember * anotherConstant;
    }       
}

8

個人的には、上に公開し、保護してから非公開にするのが好きです。これは、誰かがヘッダーをクラックして開いたときに、最初にアクセスできるものが表示され、下にスクロールすると詳細が表示されるためです。

クラスを使用するためにクラスの実装の詳細を確認する必要はありません。そうすると、クラスの設計がうまくいきません。


3

私はよく気にしていました。最近のIDEを使用してこの数年間で、ほとんどすべてが1回または2回のキーストロークだけで、標準を大幅に緩和できました。今、私は静的、メンバー変数、そしてコンストラクターから始め、その後はあまり心配しません。

C#では、Resharperに自動的に構成させます。


同意する。ファイル内のメンバーをナビゲートする通常のモードは、使用しているIDEまたはエディターに組み込まれているツールを使用することです。メンバーの実際のグループ化はセカンダリになります。ただし、メンバーをグループ化して純粋なランダムな順序付けを回避することに同意し、グループ化と順序付けを自動的に行うためにresharperを使用します。
Phillip Ngan、

2

これは私の注文になります

  1. 静的変数
  2. 静的メソッド
  3. パブリック変数
  4. 保護された変数
  5. プライベート変数
  6. コンストラクタ
  7. パブリックメソッド
  8. 保護されたメソッド
  9. プライベートメソッド

次のルールを使用します。

  • 何よりも静的
  • メソッドの前のコンストラクターの前の変数(コンストラクターはメソッドのカテゴリーにあると見なします)
  • 保護される前にパブリック、プライベートになる前

振る舞い(メソッド)の前に、オブジェクト(データ)を定義するという考え方です。staticは実際にはオブジェクトの一部ではなく、動作でもないため、分離する必要があります。


ありがとうbarkmadley ...それは面白いです!コンストラクタの前に4と5を置くことになります。私は間違いなくそれについて考えます
tempname

この順序のように、上部に静的メソッドがあることは興味深いです。私はプライベート変数を一番下に置く開発者と協力しましたが、アイデアは見えましたが、それは正しくありませんでした
Carlton

2

私は一般に、パブリック、保護、プライベートの順序、および静的データ、メンバーデータ、メンバー関数の順序に同意します。

私は時々同じようなメンバー(ゲッターとセッター)をグループ化しますが、メンバーをより簡単に見つけられるように、アルファベット順にグループ内のメンバーをリストすることをお勧めします。

データ/関数を縦に並べることも好きです。すべての名前が同じ列に配置されるように、十分に右のタブまたはスペースに移動します。


1
こんにちは-私自身の心の後の「タブスペーサー」!:-)私は強迫的ではありません。正直、私は違います!
tempname 2009年

1

Elzoが言うように、それぞれが独自に、そして最近のIDEは、ドロップダウンメニューなどの色付きアイコンを使用して、メンバーとその修飾子を簡単な方法で簡単に見つけられるようにしています。

私の見解では、プログラマーはクラスが何のために設計されたか、そしてクラスがどのように動作することが期待できるかを知ることがより重要であると考えています。

したがって、それがシングルトンの場合、セマンティクス(静的getInstance()クラス)を最初に配置します。

具体的なファクトリーの場合は、getNew()関数とレジスター/初期化関数を最初に配置します。

... 等々。最初に言うときは、c'torsとd'torの直後を意味します。これらはクラスをインスタンス化するデフォルトの方法だからです。

次に続く関数は次のとおりです。

  1. 論理呼び出し順序(例:initialize()、preProcess()、process()、postProcess())、または
  2. 関連する機能をまとめて(アクセサ、ユーティリティ、マニピュレータなど)、

クラスが主にいくつかの関数を含むデータストアであるか、いくつかのデータメンバーを含む関数プロバイダーであるかによって異なります。


0

Eclipseやその子孫などの一部のエディターでは、アウトラインビューで変数とメソッドをアルファベット順またはページのように並べ替えることができます。


0

publicに続いてprotectedとprivateのシーケンスが読みやすくなります。クラスロジックとヘッダーファイルの上部にあるコメントで簡単に説明し、関数の呼び出し順序を記述して、クラスの内部で使用されているクラスの量とアルゴリズムを理解することをお勧めします。

私はしばらくのQt C ++を使用したなどのキーワードのいくつかの新しい並べ替えを参照していますsignalし、slot私は上記のような秩序を維持し、ここにあなたと私の考えを共有することを好みます。

#ifndef TEMPLATE_H
#define TEMPLATE_H


class ClassName
{
    Q_OBJECT
    Q_PROPERTY(qreal startValue READ startValue WRITE setStartValue)
    Q_ENUMS(MyEnum)

public:

    enum MyEnum {
        Hello = 0x0,
        World = 0x1
    };

    // constructors

    explicit ClassName(QObject *parent = Q_NULLPTR);
    ~ClassName();

    // getter and setters of member variables

    // public functions (normal & virtual) -> orderby logic

public slots:

signals:

protected:

    // protected functions it's rule followed like public functions


private slots:

private:

    // methods

    // members

};

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