关于oop:如何在C ++中创建静态类?

How do you create a static class in C++?

如何在C++中创建静态类?我应该可以做一些像:

1
cout <<"bit 5 is" << BitParser::getBitAt(buffer, 5) << endl;

假设我创建了BitParser类。BitParser类定义是什么样的?


如果你正在寻找一种将"静态"关键字应用到类中的方法,比如你可以在C语言中使用,那么你就不可能不使用托管C++。

但从示例的外观来看,您只需要在BitParser对象上创建一个公共静态方法。像这样:

BitParser

1
2
3
4
5
6
7
8
9
10
11
class BitParser
{
 public:
  static bool getBitAt(int buffer, int bitIndex);

  // ...lots of great stuff

 private:
  // Disallow creating an instance of this object
  BitParser() {}
};

位PARSPR.CPP

1
2
3
4
5
6
bool BitParser::getBitAt(int buffer, int bitIndex)
{
  bool isBitSet = false;
  // .. determine if bit is set
  return isBitSet;
}

可以使用此代码以与示例代码相同的方式调用方法。

希望有帮助!干杯。


马特考虑价格的解决方案。 </P >好。

  • 在C++中,一个"静态类"已经没有意义。在最近的东西是一类以只读静态方法和成员。
  • 使用静态方法只会限制你。
  • 什么是你想要的冰,表示在C++的语义来把你的功能(它是一个功能)在一个命名空间。 </P >好。 编辑:2011年11月11日

    有没有"静态冰级"的C + +。在最近的概念,会用一只类的静态方法。例如: </P >好。

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    // header
    class MyClass
    {
       public :
          static void myMethod() ;
    } ;

    // source
    void MyClass::myMethod()
    {
       // etc.
    }

    但你必须记得,那是"静态类"是黑客的Java类的面颊部语言(例如C #)那是不能要有非成员函数,所以他们的行动,而不是对他们有作为静态内部类的方法。 </P >好。

    在C++中,什么是你真的想要的是一个非成员函数,你将在一个命名空间:DECLARE </P >好。

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    // header
    namespace MyNamespace
    {
       void myMethod() ;
    }

    // source
    namespace MyNamespace
    {
       void myMethod()
       {
          // etc.
       }
    }

    这是为什么呢?

    C++的命名空间,比冰更强大的"Java类的静态方法"的模式,因为: </P >好。

    • 静态方法的类,有私人访问的符号
    • 私人的静态方法是静止不动的(如果inaccessible)可见到每一个人,这breaches somewhat《encapsulation
    • 静态方法不能申报要求的大前锋。
    • 静态方法不能求overloaded皇家级的用户没有modifying头的图书馆
    • 有什么我可以做的冰做的由一个静态方法,能做的更好的比A(可能的朋友)功能的非成员国一样,命名空间
    • 命名空间有其自身的语义(他们可以做结合,他们可以要求匿名,等。)
    • 等。

    结论:不要拷贝/粘贴/ C,Java #’s型C + +。在Java / C #,强制型的冰。但在C + +,它的冰浴的风格。 </P >好。 编辑2010年06月10

    有一个说法是把你的静态方法,因为有时,需要使用一对一私人的静态成员变量。 </P >好。

    在disagree somewhat节目,为下面的: </P >好。 "静态的私人成员"。

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    // HPP

    class Foo
    {
       public :
          void barA() ;
       private :
          void barB() ;
          static std::string myGlobal ;
    } ;

    第一,myglobal冰被称为myglobal因为这仍然是一个全球性的私人活动。A看《clarify CPP源会是: </P >好。

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    // CPP
    std::string Foo::myGlobal ; // You MUST declare it in a CPP

    void Foo::barA()
    {
       // I can access Foo::myGlobal
    }

    void Foo::barB()
    {
       // I can access Foo::myGlobal, too
    }

    void barC()
    {
       // I CAN'T access Foo::myGlobal !!!
    }

    在一系列的事实,无功能的BARC不能访问foo myglobal表明:一个好的事情从一encapsulation观点…………………这很酷,因为有人在看着HPP不会问A(除非resorting到接入到破坏):myglobal foo。 </P >好。

    但如果你看它closely,你会发现,它是一个colossal错误:不只是你的私人的变动要求必须申报的HPP(",可见到全世界的存在,尽管存在私人),但你必须在同一个DECLARE HPP所有(As,把所有的功能是将)授权的访问信息。!!!!!!!!!!!!!! </P >好。

    SO利用私人静态成员的冰状的在外的诞生与发展战略tattooed你的恋人对你的皮肤:没有一个授权的冰,冰的触摸,但每一个人能对PEEK实习生。和奖励:每一个人能有个"授权"的名字即插即用和你的厕所。 </P >好。

    private的妈妈…… :D </P >好。 匿名名称空间溶液

    匿名名称将具有做私人事情的优势。

    okay.

    First,the HPP header

    okay.

    1
    2
    3
    4
    5
    6
    // HPP

    namespace Foo
    {
       void barA() ;
    }

    只要你确定你还活着:巴尔博或神话全球的宣言没有用处。这意味着没有人阅读主人知道巴拉背后隐藏着什么

    okay.

    Then,the CPP:

    okay.ZZU1

    正如你所看到的那样,所谓的"静态类"宣言、食品和食品仍然可以进入神话。但没有人可以。没有人会知道食物和神话甚至存在!

    okay.

    不如"静态类"在脖子上随身携带地址簿在她的皮肤上纹上"匿名"的名称空间完全封闭,看上去更容易封闭。

    okay.这是真的吗?

    Unless the users of your code are saboteurs(I'll let you,a s an exercise,find how one can access to the private part of a public class using a dirty behaviour-undefined hack…),what's privatei s edoc1〔0〕,even if it's visible in the edoc1〔0〕Class

    okay.

    但是,如果你需要增加一个"私人功能",并能进入私人成员,那么你必须通过改变头部向全世界宣布,这是一个矛盾,正如我所关心的那样:如果我改变我的代码(CPP部分),那么界面(HPP部分)就不应改变。Quoting Leonidas:"这是封装!"

    okay.2014-09-20版

    当静态类别的方法实际优于非成员函数的名称空间时?

    okay.

    When you need to group together functions and feed that group to a template:

    okay.

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    namespace alpha
    {
       void foo() ;
       void bar() ;
    }

    struct Beta
    {
       static void foo() ;
       static void bar() ;
    };

    template <typename T>
    struct Gamma
    {
       void foobar()
       {
          T::foo() ;
          T::bar() ;
       }
    };

    Gamma ga ; // compilation error
    Gamma<Beta> gb ;  // ok
    gb.foobar() ;     // ok !!!

    因为,如果一个类别可以是一个模板参数,一个名称空间不能。

    okay.好吧


    还可以在命名空间中创建自由函数:

    在BitParser

    1
    2
    3
    4
    namespace BitParser
    {
        bool getBitAt(int buffer, int bitIndex);
    }

    在bitparser.cpp中

    1
    2
    3
    4
    5
    6
    7
    namespace BitParser
    {
        bool getBitAt(int buffer, int bitIndex)
        {
            //get the bit :)
        }
    }

    一般来说,这是编写代码的首选方法。当不需要对象时,不要使用类。


    If you're looking for a way of applying the"static" keyword to a class, like you can in C# for example

    静态类只是编译器的一只手,握着你的手,阻止你编写任何实例方法/变量。

    如果你只写一个普通类,没有任何实例方法/变量,那是一样的,这就是你在C++中所做的。


    在C++中,你要创建一个类的静态函数(不是静态类)。

    1
    2
    3
    4
    5
    6
    class BitParser {
    public:
      ...
      static ... getBitAt(...) {
      }
    };

    然后,您应该能够使用bitparser::getbitat()调用函数,而无需实例化我认为是所需结果的对象。


    我能写点像static class这样的东西吗?

    不,根据C++ 11 N337标准草案附录C7.1.1:

    Change: In C ++, the static or extern specifiers can only be applied to names of objects or functions.
    Using these specifiers with type declarations is illegal in C ++. In C, these specifiers are ignored when used
    on type declarations. Example:

    1
    2
    3
    static struct S {    // valid C, invalid in C++
      int i;
    };

    Rationale: Storage class specifiers don’t have any meaning when associated with a type. In C ++, class
    members can be declared with the static storage class specifier. Allowing storage class specifiers on type
    declarations could render the code confusing for users.

    struct一样,class也是一种类型声明。

    通过浏览附录A中的语法树,可以得出相同的结论。

    有趣的是,static struct在C语言中是合法的,但没有效果:为什么以及何时在C语言编程中使用静态结构?


    你可以在C++中拥有一个静态类,正如前面提到的,静态类是一个没有任何实例化的对象的类。在C++中,可以通过将构造函数/析构函数声明为私有来获得。最终结果相同。


    在托管C++中,静态类语法是:

    1
    2
    3
    4
    5
    6
    7
    8
    public ref class BitParser abstract sealed
    {
        public:
            static bool GetBitAt(...)
            {
                ...
            }
    }

    …迟做总比不做好…


    与其他托管编程语言不同,"静态类"在C++中没有任何意义。您可以使用静态成员函数。


    这类似于C++在C++中的实现方式。

    在c file.cs中,在公共函数中可以有私有var。当在另一个文件中时,您可以通过调用具有以下函数的命名空间来使用它:

    1
    MyNamespace.Function(blah);

    下面是如何在C++中实现同样的功能:

    SharedModule

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    class TheDataToBeHidden
    {
      public:
        static int _var1;
        static int _var2;
    };

    namespace SharedData
    {
      void SetError(const char *Message, const char *Title);
      void DisplayError(void);
    }

    共享模块.cpp

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    //Init the data (Link error if not done)
    int TheDataToBeHidden::_var1 = 0;
    int TheDataToBeHidden::_var2 = 0;


    //Implement the namespace
    namespace SharedData
    {
      void SetError(const char *Message, const char *Title)
      {
        //blah using TheDataToBeHidden::_var1, etc
      }

      void DisplayError(void)
      {
        //blah
      }
    }

    其他文件

    1
    #include"SharedModule.h"

    其他文件

    1
    2
    3
    //Call the functions using the hidden variables
    SharedData::SetError("Hello","World");
    SharedData::DisplayError();


    正如这里已经注意到的,在C++中实现这一点的一个更好的方法可能是使用命名空间。但是由于这里没有人提到EDCOX1的4个关键字,所以我发布了一个直接等价于EcOX1的0个词,从C中看,在C++ 11或更后面是:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    class BitParser final
    {
    public:
      BitParser() = delete;

      static bool GetBitAt(int buffer, int pos);
    };

    bool BitParser::GetBitAt(int buffer, int pos)
    {
      // your code
    }


    当使用这些类实现继承上的组合时,名称空间对于实现"静态类"可能不太有用。命名空间不能是类的朋友,因此不能访问类的私有成员。

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    class Class {
     public:
      void foo() { Static::bar(*this); }    

     private:
      int member{0};
      friend class Static;
    };    

    class Static {
     public:
      template <typename T>
      static void bar(T& t) {
        t.member = 1;
      }
    };