問題タブ [argument-dependent-lookup]
For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.
c++ - カスタム コンテナには無料の begin/end 関数が必要ですか?
通常のルール (つまり、STL アルゴリズムで動作する、正常に動作する一般的なコードで動作するなど) で動作するカスタム コンテナー クラスを作成する場合、C++03 では、イテレーター サポートとメンバーの開始/終了関数を実装するだけで十分でした。
C++11 では、範囲ベースの for ループと std::begin/end という 2 つの新しい概念が導入されています。範囲ベースの for ループはメンバーの開始/終了関数を理解するため、C++03 コンテナーはすぐに使用できる範囲ベースの for をサポートします。アルゴリズムの場合、(Herb Sutter による「Writing modern C++ code」によると) 推奨される方法は、メンバー関数の代わりに std::begin を使用することです。
ただし、この時点で質問する必要があります-完全に修飾された begin() 関数 (つまり、std::begin(c)) を呼び出す方法と、ADL に依存して begin(c) を呼び出す方法のどちらが推奨されますか?
この特定のケースでは、ADL は役に立たないようです。可能な場合、std::begin(c) は c.begin() に委任されるため、通常の ADL の利点は適用されないようです。そして、誰もが ADL に依存し始めると、すべてのカスタム コンテナーは、必要な名前空間に追加の begin()/end() フリー関数を実装する必要があります。ただし、begin/end への非修飾呼び出しが推奨される方法であることを示唆するソースがいくつかあるようです (つまり、https://svn.boost.org/trac/boost/ticket/6357 )。
では、C++11 の方法とは何ですか? コンテナー ライブラリの作成者は、名前空間 std を使用しない場合に修飾されていない開始/終了呼び出しをサポートするために、クラスに追加の開始/終了関数を作成する必要があります。または std::begin; を使用しますか?
c++ - VS2012 の decltype 内に ADL がない
decltype を介して関数の戻り値の型を取得しようとすると、VS2012 で ADL (argument-dependent-lookup) が含まれないことに気付きました (cl.exe V17.00.60610.1 を使用してテスト)。
次の例
与える
VS2012で
しかし(予想されること):
gcc 4.7.3 で。
そのため、ADL は関数 (出力の 1 行目) を呼び出すときに機能しますが、VS2012 の decltype 内で使用すると機能しません。
それとも、別のポイントがありませんか?
c++ - 静的クラス メンバーを初期化するために使用される関数はどれですか?
静的クラス メンバーを初期化するためにどの関数を選択するかについて質問があります。
変数は、Base.cpp で定義されたものではなく、でBase::count
初期化されます。しかし、はローカルによって初期化されます。では、この場合、 Koenig ルックアップのようなルールがあるのだろうか?Base::countInit()
countInit()
local_count
countInit
c++ - Bjarne はこの ADL の例について間違っていますか、それともコンパイラのバグがありますか?
argument-dependent-lookupについて、The C++ Programming Language, 4th Edition (by Bjarne Stroustrup ) を読んでいます。これが引用です(26.3.6、過度に攻撃的なADL):
引数依存のルックアップ (ADL と呼ばれることが多い) は、冗長性を避けるために非常に役立ちます (14.2.4)。例えば:
引数依存のルックアップがなければ、
endl
マニピュレータは見つかりません。<<
そのままで、コンパイラは への最初の引数がostream
in で定義されていることに気付きますstd
。したがって、endl
instd
を検索して見つけます ( in<iostream>
)。
コンパイラによって生成された結果は次のとおりです (C++11 モード)。
これは、コンパイラまたは書籍のバグです。基準は何と言っていますか?
アップデート:
少し明確にする必要があります。正しい答えは を使用することstd::endl
です。質問は本のテキストについてでした。Lachlan Eastonが既に述べたように、これは単なるタイプミスではありません。段落全体が(おそらく)間違っています。本が他の(あまり知られていない)著者によるものであれば、この種の誤りを受け入れることができますが、Bjarneによって書かれたので、私は(そして今でも)疑問を抱いていました.
c++ - ADL 関数のアドレスを取得することはできますか?
ADL で見つけられる関数のアドレスを取得することは可能ですか?
例えば:
c++ - using ディレクティブを使用して begin と end を呼び出していますか?
呼び出すための確立されたイディオムswap
は次のとおりです。
このようにして、名前空間swap
外のユーザー定義型に対してオーバーロードできます。std
同じようにbegin
andを呼び出す必要がありますか?end
または、次のように書く必要があります。
c++ - オーバーロードされた operator== を使用した find()
オーバーロードされた operator==() を使用してベクター内の要素を見つけようとしています。ただし、type1
次のコードで使用すると、出力は 1 と 0 (見つかりません) になります。Usingtype2
は 1 と 1 の両方を返します。環境は Xubuntu 12.04 と g++ バージョン 4.6.3 です。
c++ - ADL に関する Stroustrup の新しい本にあるこの例について、説明が必要です。
Stroustrup book (第 4 版) の 396 ページと 397 ページにある引数依存ルックアップ (ADL) の例を以下に再現します。
上記のコメントが言っていることは正しいですが (私はそれをテストしました)、次の段落で著者が言っていることとは一致していないようです:
標準では、引数依存のルックアップのルールは、関連付けられた名前空間の観点から表現されています(iso §3.4.2)。基本的:
- 引数がクラス メンバーの場合、関連する名前空間は、クラス自体 (その基本クラスを含む) と、クラスを囲む名前空間です。
- 引数が名前空間のメンバーである場合、関連付けられた名前空間はそれを囲む名前空間です。
- 引数が組み込み型の場合、関連付けられた名前空間はありません。
例ではx
、 typeN::S
は class のメンバーでD
も、その baseのメンバーでもありませんBase
。しかし、それはのメンバーですnamespace N
。上記の 2 番目の箇条書きによると、関数N::f(S)
は ではなく、呼び出される関数である必要がありBase::f()
ます。
上記の結果は、標準の段落 3.4.2p2 の 2 番目の箇条書きとも一致していないようです。
T がクラス型 (共用体を含む) の場合、関連するクラスは次のとおりです。 クラス自体。もしあれば、それがメンバーであるクラス。およびその直接および間接基本クラス。関連する名前空間は、関連するクラスがメンバーになっている名前空間です。さらに、T がクラス テンプレートの特殊化である場合、それに関連付けられた名前空間とクラスには次のものが含まれます。テンプレート テンプレート引数がメンバーである名前空間。テンプレート テンプレート引数として使用されるメンバー テンプレートがメンバーであるクラス。