2

次のコードセグメントに示すように、Cスタイルの文字列でインデックス付けされたマルチマップを作成しようとしています。

    #include <cstring>
    #include <map>
    #include <iostream>

    using namespace std;

    int main(void)
    {
        int i, j;
        int (*fn_pt)(const char *, const char *) = strcmp;
        multimap<char *, char *, int (*)(const char *, const char *)>a(fn_pt);

        for (i = 0; i < 2; i++)
        {
            char key[2];
            sprintf(key, "%d", i);
            for (j = 0; j< 5; j++)
            {
                char value[2];
                sprintf(value, "%d", j);
                a.insert(pair<char *, char *>(key, value));
            }
        }

        for (i = 0; i < 2; i++)
        {
            char key[2];
            sprintf(key, "%d", i);
            multimap<char *, char *>::iterator it = a.find(key);
            while (it != a.end())
            {
                cout << it->first << "\t" << it->second <<endl;
                it++;
            }
        }
    }

上記のプログラムのキーを整数に変更するだけで、期待どおりの結果が得られます。ただし、文字列でマルチマップのインデックスを作成すると、使用されているすべてのキー値のすべての値が表示されるのではなく、予期しない結果が発生します(1と4の行のみがスペースで区切られます)。

私はこれでどこが間違っているのですか?

ありがとう

4

3 に答える 3

4

strcmpで使用するのは間違った述語multimapです。述語は以下を満たさなければならない:

式comp(a、b)は、compがこの比較クラスのオブジェクトであり、aとbがキー値である場合、厳密な弱順序操作でaをbより前の位置に配置する場合はtrueを返します。

strcmp文字列が等しくない場合、a<bまたはa>bのいずれかでゼロ以外の値を返すため、これに違反します。

最初の文字列が2番目の文字列よりも小さいtrue 場合にのみ返される、独自の述語を定義する必要があります。

于 2012-10-02T12:17:26.680 に答える
3
    multimap<char *, char *, int (*)(const char *, const char *)>a(fn_pt);

    for (i = 0; i < 2; i++)
    {
        char key[2];
        sprintf(key, "%d", i);
        for (j = 0; j< 5; j++)
        {
            char value[2];
            sprintf(value, "%d", j);
            a.insert(pair<char *, char *>(key, value));
        }
    }

コンテナに2つのポインタを格納し、スコープ外になったときにそれらのポインタが指すオブジェクト(keyおよび)を破棄します。valueこれにより、コンテナに情報が保持されたままになり、意味がなくなります。

于 2012-10-02T12:17:42.660 に答える
1

あなたは彼らがスコープから外れた後ずっとのメモリkeyを使用しています。value実際、すべてのchar*ポインタは同じスタックメモリを指しており、実際に見るまでにその部分を再利用する準備ができています。

strdup()データの永続的なコピーを作成するために使用する必要があることを実行するにはchar *。もちろん、後で割り当てを解除することについて心配する必要があります。

于 2012-10-02T12:19:05.830 に答える