2

私は C++ のソース エディターに取り組んでおり、現在編集されているステートメントの前 (基本的には、前のセミコロン/クロージングの前) のコードを無効にする必要がない単純な最適化 (強調表示、AST の再構築、静的解析の実行など) を思い付きました。ブレース) が、これが常に C++ に当てはまるかどうかはわかりません。

たとえば Java では、編集位置の後に宣言/定義された関数を呼び出すことができます。したがって、ユーザーが引数を関数に追加する場合、コード内の編集位置の前にエラー マーカーを配置する必要があります。C++ では、関数を使用する前に宣言する必要があります (宣言が定義と一致しない場合、エラーは定義上にあります)。

4

3 に答える 3

3

クラス内でインラインで定義されたメンバー関数本体は、クラスの最後で概念的に (実際には、私が知っているコンパイラで) 解析されるため、その後に宣言されたクラスのメンバーにアクセスできます。

于 2013-08-27T21:47:44.917 に答える
1

一般に、テンプレート定義の外では、C++ での名前検索の規則では、名前が使用されるポイントの前に名前を宣言する必要があります。したがって、ほとんどの場合、あなたのアイデアは機能します。残念ながら、SebastianRedl が指摘したように、この経験則が適用されない特殊なケースがあります。

クラス定義内では、クラス (およびその外側のクラス) のすべてのメンバーの宣言は、メンバー関数 (ctor-initializer-list または exception-specification を含む) の本体内での名前検索中に表示されます。メンバー関数のデフォルト引数。

実例:

struct A
{
    struct B
    {
        static void f(int i = M()) // uses 'A::M' declared later
        {
            A::f(); // calls A::f(int) declared later
        }
    };

    static void f(void*)
    {
        f(); // calls A::f(int) declared later
    }

    static void f(int i = M()) // uses 'M' declared later
    {
    }

    typedef int M;
};

変更されたトークンがメンバーの関数本体または既定の引数内にある場合は、トークンを囲むすべてのクラスを再解析する必要があります。

C++ ワーキング ドラフト標準 N3337 から:

3.4.1 非修飾名ルックアップ [basic.lookup.unqual]

関数の declarator-id に続くクラス X のメンバー関数 (9.3) の定義、またはクラス X の非静的データ メンバー (9.2) の波括弧または等号初期化子で使用される名前は、1 つの中で宣言されなければならない次の方法の:

— それが使用されているブロックまたは囲んでいるブロック(6.3)で使用される前、または

— クラス X のメンバーであるか、X の基本クラスのメンバーである (10.2)、または

— X がクラス Y (9.7) のネストされたクラスである場合、Y のメンバーであるか、Y の基底クラスのメンバーである必要があります (このルックアップは、最も内側の囲みクラスから始めて、Y の囲みクラスに順番に適用されます)。 、 また

— X がローカル クラス (9.8) またはローカル クラスのネストされたクラスである場合、クラス X の定義を囲むブロック内のクラス X の定義の前、または

— X が名前空間 N のメンバーである場合、または N のメンバーであるクラスのネストされたクラスである場合、またはローカル クラスまたは N のメンバーである関数のローカル クラス内のネストされたクラスである場合、名前空間 N または N を囲んでいる名前空間の 1 つでの名前の使用。

于 2013-08-28T13:54:05.357 に答える