开发者

Basic class templating in C++

开发者 https://www.devze.com 2023-01-31 08:36 出处:网络
I have to two class, class CFoo { public: static CFoo& GetInstance() { static CFoo instance; return instance;

I have to two class,

class CFoo
{
   public:
      static CFoo& GetInstance()
      {
         static CFoo instance;
         return instance;
      }

      int GetValue(){
         return value;
      }

   private:
      CFoo(){
         value = 0;
         ltr = 'a';
      }

      int value;
      char ltr;
};

class CBar
{
   public:
      static CBar& GetIns开发者_Python百科tance(){
         static CBar instance;
         return instance;
      }

      float GetValue(){
         return value;
      }

   private:
      CBar(){
         value = 0.4;
         ltr = 2;
      }

      float value;
      int ltr;
};

Is it possible just to create a class template for this two class , the difference is just the data types. And since the class is a singleton, how can I invoke when I create a template class for this two class? And please give example code for the basic template class.

Please advice.

Many thanks.


Generally, when you want to generalize similar classes like this, you can do so by replacing each of the types with type parameters. So, for example, here you would declare a type parameter for the type of value and a type parameter for the type of ltr.

This, obviously, looks something like:

template <typename ValueT, LtrT>
class C
{
    // ...
};

Then it's just a matter of replacing the concrete types in the class with the type parameters, so value and ltr would be declared as (inside of the class template definition):

ValueT value;
LtrT ltr;

In order to make this class template more easily usable, you can create some typedefs (outside of the class template definition):

typedef C<int, char> CFoo;
typedef C<float, int> CBar;

You also need a way to initialize the member variables. Your best bet is to make the constructor take arguments with which to initialize the member variables (inside of the class template definition):

C(const ValueT& initial_value, const LtrT& initial_ltr)
    : value(initial_value), ltr(initial_ltr) { }

Since you are trying to use a singleton, this won't work with your current (broken) implementation of GetInstance() because the function-scope static needs to be initialized in the function body. You can work around this by declaring the singleton instance as a static class member variable (inside of the class template definition):

C singleton;

then you will need to define and initialize this in one of your source files; you will need to have one definition for each instantiation of C that you use, so for the two you have here you would need:

template<> CFoo CFoo::singleton(0, 'a');
template<> CBar CBar::singleton(0.4, 2);

When you put it all together, it will look something like this (I've dumbed it down to use only a single type and value for the sake of brevity):

template <typename T>
struct S
{
public:
    S(const T& initial_value) : value(initial_value) { }

    const T& GetValue() const { return value; }

    static const S& GetInstance() { return singleton; }

private:
    // since it's a singleton, make it noncopyable
    S(const S&);
    void operator=(S);

    T value;
    static S singleton;
};

typedef S<int> SInt;

template<> SInt SInt::singleton(42);

int main()
{
    int value = SInt::GetInstance().GetValue(); 
}

Finally, and most importantly, please consider not using a singleton. Singletons are almost always A Bad Idea. It's impossible to tell what you are trying to accomplish from your stripped down example, but you should definitely try to find some other way to do it.

0

精彩评论

暂无评论...
验证码 换一张
取 消

关注公众号