2013-08-04 9 views
6

ラムダを使ってmap::compare関数をオーバーライドしようとすると、次のような解決策が働くようです。mapをオーバーライドする::ラムダ関数と直接比較する

auto cmp = [](const int&a, const int& b) { return a < b; }; 
std::map<int, int, decltype(cmp)> myMap(cmp); 

しかし、最初にcmpを定義し、後で使用する必要がありました。
'cmp'を定義せずにこれを行うことはできますか?

+2

'cmp'は関数ポインタではありません。 –

+1

Do _what_? 'int'はすでに互いに比較しています。あなたは何をしようとしているのですか?そしてなぜあなたは機能を使いたくないのですか? –

+0

ええ、関数ポインタは正確な用語ではありませんでした。質問をより明確にするために編集しました。 – MBZ

答えて

12

いいえ、あなたはできませんは評価されていないコンテキストでラムダを使用します。つまり、例のようにテンプレートパラメータです。あなたの質問は、か」についてです場合 それはすでに述べたように、あなたは、...他の方法を(autoを使用して)どこか別の場所にそれを定義し、decltypeを使用する必要がありますが、「序」ファンクタ

を使用することですラムダ式を使用するマップを定義する際に、「あなたは、このようなstd::functionにラムダの暗黙的な変換利用することができます* *たら:

#include <iostream> 
#include <functional> 
#include <map> 

int main() 
{ 
    auto m = std::map<int, int, std::function<bool(const int&, const int&)>>{ 
     [](const int& a, const int& b) 
     { 
      return a < b; 
     } 
    }; 
    return 0; 
} 

をあなたがrにそのmapタイプのエイリアスを導入することができます後で型を入力する...

+0

しかし、 'std :: function'を使用すると間接レベルが追加され、効率が低下します。 – newacct

2

マップの型が関数に渡す関数から推測されるような場合は、このようにすることができます。

#include <map> 

template<class Key, class Value, class F> 
std::map<Key, Value, F> make_map(const F& f) { 
    return std::map<Key, Value, F>{f}; 
} 

int main() { 
    auto my_map = make_map<int, int>([](const int&a, const int& b) { return a < b; }); 
    my_map[10] = 20; 
} 

私はこれを行う理由のトンを見ませんが、私はそれが役に立たないとは言いません。一般的には、マップを簡単に渡すことができるように、既知のコンパレータが必要です。もし上記の設定は、次の

tempalte<class F> 
void do_somthing(const std::map<int, int, F>& m) { 

} 

のようなテンプレート関数のすべての時間を使用して減少しているとこれは必ずしも悪いことではありませんが、私の本能はONLY汎用関数によって対処することができますタイプを持つことは悪いことを教えて。私はそれがラムダ関数のためにうまくいくと思うが、それはそれについてだ。ここでのソリューションは、今、あなたはあなたが望む任意の述語を使用することができますし、で動作するように、具体的な種類があり、

は、このことができます願っていmy_mapのstd ::機能

#include <map> 
#include <functional> 

template<class Key, class Value> 
using my_map_t = std::map<Key, Value, std::function<bool(const Key&, const Key&)>>; 

int main() { 
    my_map_t<int, int> my_map{[](const int&a, const int& b) { return a < b; }}; 
    my_map[10] = 20; 
} 

を使用することです!

あなたのマップタイプを定義して、あなたが望む比較任意のラムダを割り当てることができ、コンパレータのタイプに適切な型シグネチャを提供するために、 std::functionを使用し
6
#include <iostream> 
#include <functional> 
#include <map> 
#include <typeinfo> 

typedef std::map< int, int, std::function<bool(const int&, const int&)> > MyMap; 

int main() 
{ 
    auto cmp = [](const int& a, const int& b) { return a < b; }; 
    MyMap map(cmp); 

    return 0; 
} 

+4

これはOPが求めているものですが、実際には 'std :: function'を導入することは悪い解決策のように感じます。代わりにエイリアステンプレートはどうですか? myMap = std :: map ;を使用して 'template を実行すると、マップをインスタンス化するまでコンパレータを定義する必要はありません。 – Praetorian

+0

@Praetorian私は、テンプレートエイリアスをサポートしていない下位コンパイラ(VS2012)に悩まされているので、私は経験がありません。 – Borgleader

+0

テンプレートエイリアスはとにかく役に立ちません:__あなたは未評価のcontext__ではラムダを使用できませんが、(インスタンス化ポイントで)とにかく 'Comp'パラメータを指定する必要があります。 – zaufi

関連する問題