Seite 1 von 1

Static Class vs Static Struct vs Namespace

Verfasst: Mi Jan 30, 2013 11:58 am
von Glocke
Hi, ich habe eine prinzipiell Frage: im Quellcode habe ich ein paar (quasi globale) Variablen und Funktionen. Allerdings möchte ich die nicht im globalen Namensraum "rumliegen" haben, sondern mit Foo::value oder Foo::do() aufrufen. Welche der drei folgenden Varianten ist aus eurer Sicht die "beste"?

Variante 1: öffentliche, statische Klassenmember
Eins.hpp

Code: Alles auswählen

class Eins {
    public:
        static int value;
        static int something(int a);
};
Eins.cpp

Code: Alles auswählen

#include "Eins.hpp"

int Eins::value = 0;
int Eins::something(int a) {
    return a * a;
}
Variante 2: statische Strukturmember
Zwei.hpp

Code: Alles auswählen

struct Zwei {
    static int value;
    static int something(int a);
};
Zwei.cpp

Code: Alles auswählen

#include "Zwei.hpp"

int Zwei::value = 0;
int Zwei::something(int a) {
    return a * a;
}
Variante 3: Namespace
Drei.hpp

Code: Alles auswählen

namespace Drei {
    extern int value;
    int something(int a);
}
Drei.cpp

Code: Alles auswählen

#include "Drei.hpp"

int Drei::value = 0;
int Drei::something(int a) {
    return a * a;
}
Aufruf-Beispiel

Code: Alles auswählen

#include <iostream>

#include "Eins.hpp"
#include "Zwei.hpp"
#include "Drei.hpp"

int main() {
    Eins::value += Eins::something(5);
    std::cout << Eins::value << std::endl;
    Zwei::value += Zwei::something(5);
    std::cout << Zwei::value << std::endl;
    Drei::value += Drei::something(5);
    std::cout << Drei::value << std::endl;
}
Vom Aufruf her sind alle 3 Varianten äquivalent. Aber welche sollte ich bevorzugen und warum?

Möchte ich "interne" Daten dazunehmen (die für Außen nicht sichtbar sind), fällt die Namespace-Variante weg, richtig?

LG Glocke :mrgreen:

Re: Static Class vs Static Struct vs Namespace

Verfasst: Mi Jan 30, 2013 12:22 pm
von Xin
Glocke hat geschrieben:Vom Aufruf her sind alle 3 Varianten äquivalent. Aber welche sollte ich bevorzugen und warum?
Ich nehme Klassen, weil...
Glocke hat geschrieben:Möchte ich "interne" Daten dazunehmen (die für Außen nicht sichtbar sind), fällt die Namespace-Variante weg, richtig?
...eben dies.

Ich habe häufig Klassen in der Form

Code: Alles auswählen

class FoobarEnum
{
   int Value;
   char const * StringRepresentation;

   FoobarEnum( int value, char const * stringRepresentation )
     : Value( value ), StringRepresentation( stringRepresentation )
  {}
public:
  static FoobarEnum Snafu, FluppDiWupp;
  const int SnafuValue = 1, 
                   FluppDiWuppValue = 2;

  char const * AsString() const { return StringRepresentation );
  bool operator == ( FoobarEnum & rhs ) const { return Value == rhs.Value; }
};

// foobarenum.cpp

FoobarEnum FoobarEnum::Snafu( FoobarEnum::SnafuValue, "Snafu" );
FoobarEnum FoobarEnum::FluppDiWupp( FoobarEnum::FluppDiWuppValue, "FluppDiWupp" );

int main(void)
{
  FoobarEnum a = FoobarEnum::Snafu;
  FoobarEnum b = FoobarEnum::FluppDiWupp;

  if( a == b ) // schneller Vergleich
    printf( "a und b sind beides %s\n", a.AsString() );
  else
    printf( "a ist %s und b ist %s\n", a.AsString(), b.AsString() );

  switch( a.GetValue() )  // Schnelle Unterscheidung
  {
    case FoobarEnum::SnafuValue: printf( "Snafu!" ); break;
    case FoobarEnum::FluppDiWupp: printf( "FluppDiWupp" ); break;
    default: printf( "?" ); break;
  }
}
Ich nehme keine Structs, weil ich class hier entsprechender finde. Diese Enumklassen tragen häufig auch interessante Informationen, bzw. sind spezielle Marker. Zum Beispiel Angle::RightTurn => 270 Grad, Angle::UTurn => 180 Grad, Angle::LeftTurn => 90 Grad, oder auch Color::Red oder Point::Origin.

Da das alles Klassen sind, ist das Muster eben Klassen zu nehmen.

Mein Compiler hat eine Konfigurationsklasse. Eine Instanz davon ist als statische, globale Variable definiert. Diese eine globale Variable kann ich entsprechend fragen, wie der Compiler konfiguriert ist.

Re: Static Class vs Static Struct vs Namespace

Verfasst: Mi Jan 30, 2013 7:09 pm
von fat-lobyte
Statische Funktionen sind kein OK,
aber warum meinst du, dass du unbeding statische variablen brauchst?

Solltest du dein Programm irgendwann mal paralellisieren wollen, dann geht das oft überraschend billig - aber nicht wenn du noch irgendwo etwas statisches hast.

Re: Static Class vs Static Struct vs Namespace

Verfasst: Fr Feb 01, 2013 9:59 am
von Glocke
fat-lobyte hat geschrieben:Statische Funktionen sind kein OK,
aber warum meinst du, dass du unbeding statische variablen brauchst?

Solltest du dein Programm irgendwann mal paralellisieren wollen, dann geht das oft überraschend billig - aber nicht wenn du noch irgendwo etwas statisches hast.
Naja ich habe zum Beispiel alle Sachen die SDL zum Handeln eines Fensters bereitstellt in eine Klasse "Window" reingesteckt und mit Gettern und Setter ("setResolution", getCurrentFps" usw.) versehen. Nun will ich in anderen Teilen des Programms auf das Fenster zugreifen, ohne einen Pointer auf die Instanz mühsam überall hinschleppen zu müssen - der Aufruf "Window::setResolution(800,600)" ist mir da bequemer. Da SDL nur ein Fenster pro Anwendung unterstützt, bin ich auf die Idee der statischen Klasse gekommen. Singleton habe ich nicht in Betracht gezogen, weil ich keinen wirklichen Vorteil dadurch gesehen habe.

Naja und die Namespace-Sache ist wegen der internen Daten (die ich quasi wegkapseln möchte) aus meiner Sicht ungeeignet.

LG Glocke