ปัญหาเกี่ยวกับการสร้างอินสแตนซ์เทมเพลตที่ชัดเจน

ฉันไม่สามารถสร้างโค้ดต่อไปนี้ด้วยการคอมไพล์ Explicit Template Instantiation ได้

ฉันได้รับข้อผิดพลาดในบรรทัดนี้:

std::map<uint8_t, std::string> DW_enumDescription::descMap = std::map<uint8_t, std::string>

ด้วยเสียงดังกราวข้อผิดพลาดคือ:

ข้อผิดพลาด: ไม่มีสมาชิกชื่อ 'descMap' ใน 'O :: Data :: DW_enumDescription'

ด้วย G++ มันคือ:

ข้อผิดพลาด: ISO C++ ไม่อนุญาตให้กำหนด 'O::Data::EnumDescription::descMap' เป็น 'O::Data::DW_enumDescription::descMap' [-fpermissive]

ที่นี่ฉันใช้เนมสเปซเดิม Data ต่อไป แม้ว่าในโค้ดต้นฉบับของฉัน ฉันยังใช้เนมสเปซแยกกันสองอัน อย่างไรก็ตาม ฉันได้รับข้อผิดพลาดเดียวกัน แม้ว่าจะมีการลดความซับซ้อนนี้ก็ตาม

#include <cstdint>
#include <map>
#include <string>

namespace O
{

    namespace Data
    {

        template<typename E             /* enum to describe */
                ,typename T = uint8_t   /* index type */
                >
        class EnumDescription
        {
        public:
            /// Static map to store the descriptions
            static std::map<T, std::string> descMap;
        };
    }
}

namespace O
{
    namespace Data
    {

        enum struct DW : uint8_t
        {
            DW_Unknown = 0,
            DW_TS_1    = 1,
            DW_TS_2    = 2,
            DW_DS_1    = 3,
            DW_Dev     = 4,
            enumSize   = 5
        };

        class DW_enumDescription : public Data::EnumDescription<DW, uint8_t> {};

    }
}


// ===================== Explicit Template Instantiation ======================
namespace O
{
    template class Data::EnumDescription<Data::DW, uint8_t>;
}
// ============================================================================

namespace O
{
    namespace Data
    {
        std::map<uint8_t, std::string> DW_enumDescription::descMap = std::map<uint8_t, std::string> // ERROR
        {
            { static_cast<uint8_t>(DW::DW_Unknown), "Unknown" },
            { static_cast<uint8_t>(DW::DW_TS_1),    "DW_TS_1" },
            { static_cast<uint8_t>(DW::DW_TS_2),    "DW_TS_2" },
            { static_cast<uint8_t>(DW::DW_DS_1),    "DW_DS_1" },
            { static_cast<uint8_t>(DW::DW_Dev),     "DW_Dev"  },
        };
    }
}

person Pietro    schedule 16.09.2019    source แหล่งที่มา


คำตอบ (1)


descMap เป็นสมาชิกของ EnumDescription<DW, uint8_t> ดังนั้น การแก้ไข:

namespace O
{
    namespace Data
    {
        template<> std::map<uint8_t, std::string> EnumDescription<DW, uint8_t>::descMap =
        {
            { static_cast<uint8_t>(DW::DW_Unknown), "Unknown" },
            { static_cast<uint8_t>(DW::DW_TS_1),    "DW_TS_1" },
            { static_cast<uint8_t>(DW::DW_TS_2),    "DW_TS_2" },
            { static_cast<uint8_t>(DW::DW_DS_1),    "DW_DS_1" },
            { static_cast<uint8_t>(DW::DW_Dev),     "DW_Dev"  },
        };
    }
}
person Maxim Egorushkin    schedule 16.09.2019
comment
เป็นเพราะสมาชิกแบบสแตติกของคลาสจะต้องเตรียมใช้งานในคลาสของตัวเอง (และไม่ใช่คลาสที่ได้รับมา) และ EnumDescription<DW, uint8_t> สอดคล้องกับฐาน ในขณะที่ DW_enumDescription เป็นคลาสที่ได้รับมาใช่หรือไม่ - person Pietro; 18.09.2019