वहाँ एक पैटर्न है जहाँ मैं सी + + में एक और एनम से Enum वारिस कर सकते हैं ??
ऐसा कुछ:
enum eBase
{
one=1, two, three
};
enum eDerived: public eBase
{
four=4, five, six
};
वहाँ एक पैटर्न है जहाँ मैं सी + + में एक और एनम से Enum वारिस कर सकते हैं ??
ऐसा कुछ:
enum eBase
{
one=1, two, three
};
enum eDerived: public eBase
{
four=4, five, six
};
जवाबों:
संभव नहीं। एनम के साथ कोई विरासत नहीं है।
इसके बजाय आप नामित कॉन्स्ट इन्ट्स वाली कक्षाओं का उपयोग कर सकते हैं।
उदाहरण:
class Colors
{
public:
static const int RED = 1;
static const int GREEN = 2;
};
class RGB : public Colors
{
static const int BLUE = 10;
};
class FourColors : public Colors
{
public:
static const int ORANGE = 100;
static const int PURPLE = 101;
};
Colors
वर्ग उदाहरणों का उपयोग नहीं करेंगे । आप केवल स्थैतिक कांस्टेबल सदस्यों में अंतर मान का उपयोग करते हैं।
Color
, जैसे आप एक के लिए कर सकते हैं enum
।
#include <iostream>
#include <ostream>
class Enum
{
public:
enum
{
One = 1,
Two,
Last
};
};
class EnumDeriv : public Enum
{
public:
enum
{
Three = Enum::Last,
Four,
Five
};
};
int main()
{
std::cout << EnumDeriv::One << std::endl;
std::cout << EnumDeriv::Four << std::endl;
return 0;
}
int basic(EnumBase b) { return b; }
और int derived(EnumDeriv d) { return d; }
, उन प्रकारों को परिवर्तनीय नहीं किया जाएगा int
, हालांकि सादे एनम हैं। और जब आप इस तरह के एक भी सरल कोड की कोशिश करते हैं: cout << basic(EnumBase::One) << endl;
तो, आपको एक त्रुटि मिलेगी conversion from ‘EnumBase::<anonymous enum>’ to non-scalar type ‘EnumBase’ requested
:। कुछ रूपांतरण ऑपरेटरों को जोड़कर शायद उन समस्याओं को दूर किया जा सकता है।
आप सीधे ऐसा नहीं कर सकते, लेकिन आप इस लेख से समाधान का उपयोग करने की कोशिश कर सकते हैं ।
मुख्य विचार सहायक टेम्प्लेट क्लास का उपयोग करना है, जो एनम मान रखता है और जिसमें टाइप कास्ट ऑपरेटर होता है। यह मानते हुए कि एनम के लिए अंतर्निहित प्रकार int
आप इस धारक वर्ग को एनम के बजाय अपने कोड में मूल रूप से उपयोग कर सकते हैं।
दुर्भाग्य से यह C ++ 14 में संभव नहीं है। मुझे उम्मीद है कि हमारे पास C ++ 17 में ऐसी भाषा सुविधा होगी। जैसा कि आप पहले से ही अपनी समस्या के लिए कुछ समाधान मैं एक समाधान प्रदान नहीं करेगा।
मैं यह बताना चाहता हूं कि शब्द "विस्तार" होना चाहिए न कि "वंशानुक्रम"। विस्तार अधिक मूल्यों के लिए अनुमति देता है (जैसा कि आप अपने उदाहरण में 3 से 6 मानों से कूद रहे हैं) जबकि विरासत का अर्थ है किसी दिए गए आधार वर्ग में अधिक अवरोध डालना ताकि संभावनाओं का समूह सिकुड़ जाए। इसलिए, संभावित कास्टिंग विरासत से बिल्कुल विपरीत काम करेगी। आप व्युत्पन्न वर्ग को आधार वर्ग में डाल सकते हैं, न कि वर्ग उत्तराधिकार के साथ उलटा। लेकिन एक्सटेंशन होने पर आपको "क्लास" को अपने एक्सटेंशन में ले जाने में सक्षम होना चाहिए, न कि इसके विपरीत। मैं कह रहा हूँ "चाहिए" क्योंकि, जैसा कि मैंने कहा कि इस तरह की भाषा की सुविधा अभी भी मौजूद नहीं है।
extends
एफिल भाषा में वंशानुक्रम के लिए एक कीवर्ड है।
इस बारे में कैसा है? ठीक है एक उदाहरण हर संभव मूल्य के लिए बनाया गया है, लेकिन इसके अलावा यह बहुत लचीला है। क्या कोई डाउनसाइड है?
.h:
class BaseEnum
{
public:
static const BaseEnum ONE;
static const BaseEnum TWO;
bool operator==(const BaseEnum& other);
protected:
BaseEnum() : i(maxI++) {}
const int i;
static int maxI;
};
class DerivedEnum : public BaseEnum
{
public:
static const DerivedEnum THREE;
};
.cpp:
int BaseEnum::maxI = 0;
bool BaseEnum::operator==(const BaseEnum& other) {
return i == other.i;
}
const BaseEnum BaseEnum::ONE;
const BaseEnum BaseEnum::TWO;
const DerivedEnum DerivedEnum::THREE;
उपयोग:
BaseEnum e = DerivedEnum::THREE;
if (e == DerivedEnum::THREE) {
std::cerr << "equal" << std::endl;
}
BaseEnum::i
सार्वजनिक और BaseEnum::maxI
निजी भी किया ।
यदि आप enum
व्युत्पन्न वर्ग में एक ही नाम के साथ परिभाषित करते हैं और इसे enum
आधार वर्ग में संवाददाता के अंतिम आइटम से शुरू करते हैं , तो आप लगभग वही प्राप्त करेंगे जो आप चाहते हैं - विरासत में मिला एनम। इस कोड को देखें:
class Base
{
public:
enum ErrorType
{
GeneralError,
NoMemory,
FileNotFound,
LastItem,
};
};
class Inherited: public Base
{
public:
enum ErrorType
{
SocketError = Base::LastItem,
NotEnoughBandwidth,
};
};
जैसा कि कहा गया है bayda
, Enum की (और / या नहीं) की कार्यक्षमता होनी चाहिए, इसलिए मैंने निम्नलिखित Mykola Golubyev
प्रतिक्रिया को स्वीकार करते हुए आपके प्रश्न के लिए निम्नलिखित दृष्टिकोण लिया है :
typedef struct
{
enum
{
ONE = 1,
TWO,
LAST
};
}BaseEnum;
typedef struct : public BaseEnum
{
enum
{
THREE = BaseEnum::LAST,
FOUR,
FIVE
};
}DerivedEnum;
विस्तार योग्य गणना बनाने के लिए आप प्रोजेक्ट SuperEnum का उपयोग कर सकते हैं ।
/*** my_enum.h ***/
class MyEnum: public SuperEnum<MyEnum>
{
public:
MyEnum() {}
explicit MyEnum(const int &value): SuperEnum(value) {}
static const MyEnum element1;
static const MyEnum element2;
static const MyEnum element3;
};
/*** my_enum.cpp ***/
const MyEnum MyEnum::element1(1);
const MyEnum MyEnum::element2;
const MyEnum MyEnum::element3;
/*** my_enum2.h ***/
class MyEnum2: public MyEnum
{
public:
MyEnum2() {}
explicit MyEnum2(const int &value): MyEnum(value) {}
static const MyEnum2 element4;
static const MyEnum2 element5;
};
/*** my_enum2.cpp ***/
const MyEnum2 MyEnum2::element4;
const MyEnum2 MyEnum2::element5;
/*** main.cpp ***/
std::cout << MyEnum2::element3;
// Output: 3
const int&
int
हैक की तरह है, लेकिन यह है कि मैं के साथ आया था अगर scoped enums के साथ काम:
enum class OriginalType {
FOO, // 0
BAR // 1
END // 2
};
enum class ExtendOriginalType : std::underlying_type_t<OriginalType> {
EXTENDED_FOO = static_cast<std::underlying_type_t<OriginalType>>
(OriginalType::END), // 2
EXTENDED_BAR // 3
};
और फिर जैसे उपयोग करें:
OriginalType myOriginalType = (OriginalType)ExtendOriginalType::EXTENDED_BAR;
यह उत्तर ब्रायन आर। बॉन्डी उत्तर का एक प्रकार है। चूंकि मुझे एक टिप्पणी में अनुरोध किया गया है, मैं इसे उत्तर के रूप में जोड़ रहा हूं। अगर यह वास्तव में लायक है, तो मैं इसके बारे में नहीं बता रहा हूं।
#include <iostream>
class Colors
{
public:
static Colors RED;
static Colors GREEN;
operator int(){ return value; }
operator int() const{ return value; }
protected:
Colors(int v) : value{v}{}
private:
int value;
};
Colors Colors::RED{1};
Colors Colors::GREEN{2};
class RGB : public Colors
{
public:
static RGB BLUE;
private:
RGB(int v) : Colors(v){}
};
RGB RGB::BLUE{10};
int main ()
{
std::cout << Colors::RED << " " << RGB::RED << std::endl;
}
enum xx {
ONE = 1,
TWO,
xx_Done
};
enum yy {
THREE = xx_Done,
FOUR,
};
typedef int myenum;
static map<myenum,string>& mymap() {
static map<myenum,string> statmap;
statmap[ONE] = "One";
statmap[TWO] = "Two";
statmap[THREE] = "Three";
statmap[FOUR] = "Four";
return statmap;
}
उपयोग:
std::string s1 = mamap()[ONE];
std::string s4 = mymap()[FOUR];