繁体   English   中英

const char数组多重初始化C ++

[英]const char array multiple initialization c++

我在Base类中有一个const char数组。

static const char *_myArray[10];

我创建了一个子Child1类的CPP文件,并可以使用以下语法初始化_myArray[10]

const char *Base::_myArray[10] = {"red", "green", "blue"};

我创建了另一个子名称Child2并且需要使用{"pink", "yellow", "brown"}值初始化该数组。

我在Child2类似的Child2 ,但是,无法使用这种方式初始化数组。 多重初始化存在问题,产生编译错误。

我在我的基本类实例中使用此数组(从派生类进行广播),并且应从派生类填充数据(因为每个子代的数据可能有所不同)。

解决该问题的正确方法是什么? 非常感谢您的支持。

先感谢您!

静态变量只能初始化一次。 初始化静态成员时,您告诉编译器此静态变量在哪个编译单元中。 您已经在Child1中初始化了变量,而在Child2中则无法完成。

您的问题是static关键字。 这意味着该类的所有实例都共享一个数组(如果声明为public,则该数组甚至可以在没有任何实例的情况下访问)。 因此,您可以使用{"red", "green", "blue"}初始化数组,此后,由于数组为const因此无法再进行更改。 然后尝试使用{"pink", "yellow", "brown"}再次初始化它{"pink", "yellow", "brown"}这将导致错误。

为什么这个数组必须是静态的? 删除static并在构造函数的初始化列表中进行初始化。

这是此方法的正确语法:

Base::Base() : _myArray{"red", "green", "blue"} 
{
    // Constructor here
}

我还注意到的问题是,您将这个一维数组二维处理。 数组的每个单元只能存储一个字符,而不是C-String。 您可以通过使用二维数组或通过使用std::strings数组来解决此问题。

有一些方法可以解决此问题:一种方法是每次在类中显式编写静态成员:

class Base {/*...*/};

class InheritedFirst : public Base
{
    static constexpr const char* _myArray[10] = {"First"};
};

class InheritedSecond : public Base
{
    static constexpr const char* _myArray[10] = {"Second"};
};

另一个方法是从模板类中获取当前类作为模板参数:

class Base {/*...*/};

template<typename T>
class GimmeArray
{
    static const char* _myArray[10];
};

class InheritedThird : public Base, public GimmeArray<InheritedThird>
{/*...*/};

class InheritedFourth : public Base, public GimmeArray<InheritedFourth>
{/*...*/};

template<typename T>
const char* GimmeArray<T>::_myArray[10] = {"Not specialized"};
template<>
const char* GimmeArray<InheritedThird>::_myArray[10] = {"Third"};
template<>
const char* GimmeArray<InheritedFourth>::_myArray[10] = {"Fourth"};

目的:

提供一个单词数组,每个派生类存储一次。 同一类的所有实例应共享相同的单词数组。

对共享数组的访问应是多态的,以便观察者可以在不知道对象确切类型的情况下访问数组。

在这种情况下,我将在基类上具有一个非多态接口函数,该函数遵照多态实现。

该实现将在每个派生类中定义一次,并且应充当对静态const单词数组的引用。

作为静态常量,c ++将保证它是在首次使用时创建的。 c ++ 11将保证构造是原子的。

像这样的东西:

#include <array>
#include <iostream>
#include <memory>

using words_array = std::array<const char*, 3>;

struct has_words_base
{
public:
    const words_array& get_words() const
    {
        return get_words_impl();
    }

private:
    virtual const words_array& get_words_impl() const
    {
        static const words_array _ { "grey", "black", "brown" };
        return _;
    }

};

struct blue_words : has_words_base
{
private:
    virtual const words_array& get_words_impl() const override
    {
        static const words_array _ { "blue", "cyan", "indigo" };
        return _;
    }

};

struct red_words : has_words_base
{
private:
    virtual const words_array& get_words_impl() const override
    {
        static const words_array _ { "red", "vermillion", "scarlet" };
        return _;
    }
};


void test(const has_words_base& ob)
{
    auto sep = "";
    for (auto&& w : ob.get_words()) {
        std::cout << sep << w;
        sep = ", ";
    }
    std::cout << std::endl;

}

int main()
{
    test(*std::make_unique<has_words_base>());
    test(*std::make_unique<blue_words>());
    test(*std::make_unique<red_words>());

}

预期输出:

grey, black, brown
blue, cyan, indigo
red, vermillion, scarlet

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM