Making a logger accessable to all classes?

Started by
28 comments, last by colinisinhere 19 years, 7 months ago
or you could make the logging a "policy" and then combine it with whatever logging approach you want to use.

that way clients that don't want or need logging can use a null policy and have all logging optimized away
HardDrop - hard link shell extension."Tread softly because you tread on my dreams" - Yeats
Advertisement
Quote:Original post by Kibble
operator -> and operator * cannot be statics, however the error I recall is something informing you of that. Possibly the templates are messing with the compiler's errors or something, but I am sure that operator -> and operator * can't be statics.

edit: Well DUUUUUUUUUUUUUUUUUUUURRRRR it has it right there, I must be blind. sorry for the stupidity.


doh! now why the heck would they go and implement such a silly limitation as that? (in seriousness, I _am_ curious...)

To get the template mojo I posted to work, remove "static" from the decleration of both operators... also, you'll want to replace:

template <typename SingletonT> SingletonT Singleton::singleton;


with:

template <typename SingletonT> SingletonT Singleton<SingletonT>::singleton;


and this time I blurdy tested it, and it compiles and runs ;-).
But a monostate has the same flexibility as a singleton - you change the underlying function's implementation and the rest of the world is none the wiser. Smells like polymorphism to me.
--God has paid us the intolerable compliment of loving us, in the deepest, most tragic, most inexorable sense.- C.S. Lewis
Quote:Original post by antareus
But a monostate has the same flexibility as a singleton - you change the underlying function's implementation and the rest of the world is none the wiser. Smells like polymorphism to me.


That's nowhere close to polymorphism. Changing some code you wrote that sits inside a global function and accesses global variables is... well it's plain C coding. There's nothing remotely polymorphic about it. Everything is decided at compile-time. By putting a class around it, all you really gain is a namespace and the ability to hide those global variables from the rest of the code. Other than that, it's plain C coding, and in poor style because you have [edit]a lot of[/edit] global variables.

Polymorphism decides which of several functions to call at run-time. Of course, you can do the same thing with function pointers in straight C, but the code to do that is a lot messier. It's nice to have the C++ compiler take care of that for you, along with all the nice inheritance logic implemented so you don't have to deal with it. (Just because almost any language feature can be duplicated in almost any other language doesn't mean it's worth doing it.)
Oh yeah, I almost forgot my original point. When creating a singleton, it is much better to have a static pointer to your class than a static object. You can't control the order in which global object's constructors/deconstructors get called, which can cause problems if you're not careful. If you have a static pointer to an object, then you can initialize/uninitialize/re-initialize it when you need to, and in the proper order.

And as stated above, you get the ability to use virtual functions. So you can write a CFileLogger, a CDatabaseLogger, a CSyslogLogger, and so on, and switch between them if you want at run-time.

As a side-note, loggers should always have different logging levels. For normal runs you may set the logging level fairly low, but then crank it up when you're hunting something specific down (without having to recompile). This is especially useful when the product goes out into the field and an end-user has a problem. Macros that check the logging level before calling the logging function can make it pretty safe to put logging calls in all but the most performance-sensitive code.

I have a question about global variables.

Are objects semi global if I declear a pointer to it in a class?

ea:
class A{  public:            A( object1* obj );            void DoStuff( void );   private:            object1* obj;};


So I should use:
class B{  public:            A( void );            void DoStuff( object1* obj);   private:};


?
I haven't heard of the Flywheel pattern. I tried googling, but all I get is a bunch of automotive stuff.
daerid@gmail.com
Quote:Original post by rakoon2
I have a question about global variables.

Are objects semi global if I declear a pointer to it in a class?

No, that doesn't make them semi-global. Depending on what you're doing, sometimes it's better to store the object as a member variable (whether by value, pointer, or reference), and sometimes it's better to pass it into a method.
Yes, I know.

But what about a Monster(Ingame consol) class, the class itself doesn't need "global" acess to the player informations, ..

So I just send the informations to the class.

monster->update( player->getX(), player->getY() );




So should I use "semi-global" object pointer only if it fits into the concept!
( ea an animated sprite class with pointers to the sprites )
wow, thanks for all of the replies!! I got it working! But I think I need to brush up on my pointers and statics etc, cuz I don't fully understand the code....

thanks!

This topic is closed to new replies.

Advertisement