dimanche 4 novembre 2018

Variadic templates and Tree

I have next command:

auto result = Builder::get(
        ObjKey("key1"),
        ObjVal("test1"),
        (ObjKey("key2"), ObjVal("test21"), (ObjKey("key3"), ObjVal("test31"), ObjVal("test32")), ObjVal("test22")),
        ObjVal("test2")
    );

I expect to get the following result:

{key1, test1, {key2, test21, {key3, test31, test32}, test22}, test2}

but I get this result:

{key1, test1, test22, test2}

The program code is below (standard 11):

#include <iostream>

class ObjKey {
public:
    ObjKey() = delete;

    ObjKey(const std::string& key) : m_key(key) { }

    std::string get() const {
        return m_key + ", ";
    }

private:
    std::string m_key;
};

class ObjVal {
public:
    ObjVal() = delete;

    ObjVal(const std::string& value) : m_value(value) { }

    std::string get() const {
        return m_value + ", ";
    }

private:
    std::string m_value;
};

class Builder {
public:
    template<typename... Args>
    static std::string get(ObjKey&& objKey, Args&& ...args) {
        std::string resultValue;
        get(resultValue, std::forward<ObjKey>(objKey), std::forward<Args>(args)...);
        return resultValue;
    }

private:
    Builder() {}

    template<typename... Args>
    static void get(std::string& resultValue, ObjKey&& objKey, Args&& ...args) {
        resultValue.append("{");
        resultValue.append(objKey.get());
        std::string values;
        get(values, std::forward<Args>(args)...);
        resultValue.append(values);
        resultValue.append("}");
    }

    template<typename... Args>
    static void get(std::string& resultValue, ObjVal&& objVal, Args&& ...args) {
        resultValue.append(objVal.get());
        get(resultValue, std::forward<Args>(args)...);
    }

    static void get(std::string& resultValue) {}
};

int main()
{
    auto result = Builder::get(
        ObjKey("key1"),
        ObjVal("test1"),
        (ObjKey("key2"), ObjVal("test21"), (ObjKey("key3"), ObjVal("test31"), ObjVal("test32")), ObjVal("test22")),
        ObjVal("test2")
    );
    std::cout << result << "\n";
}

What am i doing wrong?

And is it possible to solve with templates?

Aucun commentaire:

Enregistrer un commentaire