問題タブ [function-object]
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++ - (関数オブジェクト)クラス(変数)テンプレートによる関数ラッパー
C++
(関数オブジェクト) クラス (バリアディック) テンプレートを介して関数ラッパーを実装しようとしています。このクラスは、唯一のデータ メンバとして、ラップしている関数ポインタによって初期化されるか割り当てられた関数ポインタを持っています。パラメーター化されたコンストラクターは、関数ポインターを受け取り、それによってメンバーを初期化します。operator()
メソッドは引数を取り (またはなし)、ラップされた関数を呼び出します。少なくともそれがアイデアです。多くのエラーが発生するので、コメントでマークします。VC11 (2012 年 11 月の CTP で、可変個引数テンプレートを有効にする) はerror C2091: function returns function
、マークされた領域の 1 つを除くすべてで私を与えてくれます。最後のエラーは異なります。コード内でその完全な説明をコメントします。g++ では、コード番号が異なりますが、ほとんど同じエラーが発生します。
これらのエラーが発生するのはなぜですか? たとえば、パラメーター化されたコンストラクターが何かを返す方法や、データ メンバーの宣言が何かを返す方法がわかりません。データメンバ宣言が関数ポインタ宣言になっていませんか? たとえば、を受け取って?を返すint (*g)(int);
関数を指すポインターを宣言しません。int
int
編集/補遺:
答えからわかるのは、それint(int, int)
は 1 つのタイプのみであり、目的の効果を得るには部分的な特殊化が必要であるということです。しかし、私のコードでエラーが発生するのは何ですか? コメントアウトしてmyfunc = foo
も、他のエラーが発生します。func<int(int, int)> myfunc;
デフォルトのコンストラクターを呼び出します。typename R
にインスタンス化されint(int, int)
、typename... Tn
空になります。データ メンバは にR (*fptr)(Tn...);
なるためR (*fptr)();
、fptr
引数を 0 とって を返す関数を指す関数ポインタになりますR
。R
がint(int, int)
の場合R
、関数ポインタ型ですか、それとも関数型ですか? 後者の場合、エラー メッセージのコンテキストを理解できます。
c++ - std::set - コンテナー内の関数オブジェクトのサポートと同様
独自のコンテナを実装しました:
私がやりたいのは、std::set のように、関数オブジェクトのサポートを追加することです。ここでは、次のような関数オブジェクトを実行できます。
そしてそれを設定パラメータとして渡します:
私は毎日の C++ プログラマーではないので、それを達成するには助けが必要です。これにサポートを追加するには、どうすればよいですか? MyContainer
関数オブジェクトを格納してコンテナー内のソート メソッドで使用するには、フィールドを作成する必要がありますか?
c++ - const および非 const ファンクター
これは頻繁に尋ねられて答えられるべきもののように思えますが、私の検索法は失敗しました。
ある種の汎用呼び出し可能オブジェクト (裸の関数、手巻きのファンクター オブジェクト、bind
、またはを含む) を受け入れstd::function
、アルゴリズムの深さ (つまり、ラムダ) 内でそれを呼び出したい関数を作成しています。
関数は現在、次のように宣言されています。
関数へのエントリでファンクターがコピーされないことを保証したいので、参照によってファンクターを受け入れます。したがって、オブジェクトの同じインスタンスが実際に呼び出されます。これは、一時オブジェクトを受け入れる唯一の方法であるため、これは const 参照です (これは、手巻きファンクターまたは を使用する場合に一般的ですbind
)。
ただし、これにはファンクターoperator()
が const として実装する必要があります。私はそれを要求したくありません。どちらも受け入れられるようにしたいです。
両方のケースをカバーするために、このメソッドの 2 つのコピーを宣言できます。1 つは const として受け入れ、もう 1 つは非 const として受け入れます。しかし、コメントには複製したくないコードがかなり隠されているため、そうしたくありません (いくつかのループ構造を含むため、問題を移動するだけでそれらを二次メソッドに抽出することはできません)。 .
また、呼び出す前にファンクターを非 const にする可能性があることも知ってconst_cast
いますが、これは潜在的に危険だと感じています (特に、ファンクターが const 呼び出し演算子と非 const 呼び出し演算子の両方を意図的に実装している場合は、間違ったメソッドを呼び出す可能性があります)。
std::function
ファンクターを/として受け入れることを検討しましたboost::function
が、これは単純な問題であるべき問題に対する重い解決策のように感じます。(特に、ファンクタが何もしないことになっている場合。)
アルゴリズムを複製する以外に、これらの要件を満たす「正しい」方法はありますか?
[注: C++11 を必要としないソリューションを希望しますが、両方の言語のプロジェクトで同様の構成を使用しているため、C++11 の回答にも興味があります。]
c++ - ファンクター: テンプレート化された struct とテンプレート化された operator()
標準ライブラリ関数オブジェクトの通常のパターンは、テンプレート化された構造体に非テンプレートを使用することoperator()
です。たとえば、std::less
次のようになります。
私の質問は、なぜこれがテンプレート化された非テンプレート構造体よりも優れているのoperator()
ですか? 上記のファンクターは、次の操作と同等であるように思われます。
ただし、自動型控除のボーナスが得られます。さらに良いことに、必要に応じて、異なるタイプを比較することもできます。
そしてそこから、たとえばdecltype
真に汎用的な を取得するために使用する方法は明らかです。std::plus
しかし、標準ライブラリはそのようにはしません。
もちろん、私はこれが最初に起こった人ではなく、標準化委員会が 2 番目ではなく 1 番目のパターンを採用することを決定した非常に正当な理由があると確信しています。私はそれが何であるか分かりません。教祖の誰かが私を啓発することができますか?
c++ - N3421 が noexcept 修飾子を提供しないのはなぜですか?
N3421 - Making Operator Functors greater<>では、std 関数オブジェクトの新しい特殊化は次のとおりです。
それ以外の
- その理由はありますか?
noexcept
このユースケースで問題の省略はありますか?
編集: github の作業ドラフト行へのリンク。
編集 2: libc++ と特殊化へのリンク。
c++ - ユーザー定義の比較とランダム アクセス イテレータを使用した std::map の make_heap
このように定義されたマップがあります
このマップを処理した後、(2 番目の値に基づいて) ヒープとして扱いたいと思います。std::make_heap 関数を使用することにしました。これは次のように定義されています...
この関数には比較関数を定義する必要があるため...私はこのようにしました
このセットアップで、このように make_heap を呼び出します
しかし、これによりコンパイルエラーが発生します...
コンパイル エラーは、make_heap が random_access_iterator を必要としていることが原因である可能性があるというヒントを与えてくれますが、それについてはわかりません。
(単純な関数ポインターから) 関数オブジェクトに移動する必要がありますか?
何か助けはありますか?
c++ - C++ の funcall : 関数をパラメーターとして受け取る関数の宣言
std::count など、STL を使用して関数または関数オブジェクトをパラメーターとして渡す例がウェブ上にたくさんあります。
そのような引数を取る独自の関数を作成するにはどうすればよいですか?
簡単な例として、私のクラスは次のとおりです。
次のような関数 funcall を定義したいと思います。
ここで、宣言「機能」は、とりわけ、私が確信していないものです。「funcall」という用語は Lisp に由来し、引数 ab cに(funcall f a b c)
のみ適用されます。f
次に、次のようなものが機能するはずです。
これを達成するための簡単な方法は何ですか?
私はこれらをデバッグ ヘルパーとして作成しています。「funcall」は、count、remove-if、transform など、関数の引数を取る STL 関数のような、独自のデータ構造のアナログのような独自の実装の一部として使用されます。しかし、複雑なテンプレート式を記述してコードを定義したくありません。
この質問に対する最初の回答は、少なくとも私にとっては、関数の引数を宣言して使用するという概念全体が少し曖昧であることを示唆しています。おそらく funcall に対処する前に、関数の引数を別の関数に渡すだけで、それを使用しない方が簡単な作業になるかもしれません。たとえば、C++ でベクトル v を数えるには、次のように書く必要があります。
次のように、常にベクトル全体をカウントするカウントをどのように書くことができますか?
上と同じですか?そして、この「mycount」は、ラムダの代わりにメンバー関数ポインターに対して機能しますか?
この質問は基本的に「funcall」の質問と同じですが、渡された関数オブジェクトを実際に呼び出す必要はありません。
javascript - 関数とオブジェクトのどちらが先ですか?
このオブジェクト レイアウト図では、javascript でプロトタイプ チェーンをうまく説明しています。しかし、次の関係については少し混乱します。
- 関数オブジェクト(){}
- オブジェクトのプロトタイプ
- 関数関数(){}
- Function.prototype
私の質問は、上記の 4 つの要素のうち、最初に来るのはどれですか? それらの間にサイクルが見えるからです。
- 関数 Object.____proto____ -> Function.prototype
- Function.prototype.____proto____ -> Object.prototype
- Object.prototype.constructor -> 関数オブジェクト
また、別のサイクルは次のとおりです。
- Function.prototype.constructor -> 関数 関数
- 関数 Function.____proto____ -> Function.prototype
そんなことがあるものか?