简体   繁体   English

例化 Qt 基于文件的记录器以在 C++ 库中进行调试

[英]Instantiating a Qt File-Based Logger for Debugging in a C++ Library

The following page provides a nice simple solution for file based logging in Qt for debugging without using a larger logging framework like the many that are suggested in other SO questions.以下页面为Qt 中的基于文件的日志记录提供了一个很好的简单解决方案,用于在不使用其他 SO 问题中建议的许多更大的日志记录框架的情况下进行调试。

I'm writing a library and would like to instantiate a logger that the classes in the library can use (mostly for debugging purposes).我正在编写一个库,并希望实例化一个库中的类可以使用的记录器(主要用于调试目的)。 There is no int main() function since it's a library.没有int main() function 因为它是一个库。 So would the best approach be to add the instantiation into a file like logger.h and have any classes include logger.h if it would like to do qDebug() << PREFIX << "Bla" as the link above suggests?那么最好的方法是将实例化添加到像logger.h这样的文件中,并且如果它想像上面的链接那样执行qDebug() << PREFIX << "Bla" ,那么任何类都包括logger.h吗?

I pretty much agree with OrcunC but I'd recommend making that ofstream a little more accessible and capable of handling the Qt value types.我非常同意 OrcunC,但我建议让ofstream更易于访问,并且能够处理 Qt 值类型。

Here's my recommended process:这是我推荐的过程:

  1. Create a global QIODevice that to which everything will be written.创建一个全局QIODevice ,所有内容都将写入其中。 This will probably be a QFile.这可能是一个 QFile。
  2. Create a QTextStream wrapper around that QIODevice that you'll then use for all the logging.围绕该 QIODevice 创建一个QTextStream包装器,然后将其用于所有日志记录。
  3. If you want something slightly more complicated, create methods that do the filtering based on log level info.如果您想要稍微复杂一点的东西,请创建基于日志级别信息进行过滤的方法。

For example:例如:

// setup the global logger somewhere appropriate
QFile *file = new QFile("your.log");
file->open(QIODevice::ReadOnly);
QTextStream *qlogger = new QTextStream(file);

And once the global logger is initialized, you could reference it as a global:一旦全局记录器被初始化,你可以将它作为一个全局引用:

#include "qlogger.h"
//... and within some method
*qlogger << "your log" << aQtValueType;

But you might want some filtering:但是您可能需要一些过滤:

#include "qlogger.h"
// lower number = higher priority
void setCurrentLogLevel(int level) {
   globalLogLevel = level;
}
QTextStream* qLog(int level) {
   if (level <= globalLogLevel) {
       return qlogger;
   }
   return getNullLogger(); // implementation left to reader
}

And then you'd likely create an enum that represented the LogLevel and do something like this:然后您可能会创建一个代表 LogLevel 的枚举并执行以下操作:

#include "qlogger.h"
//...
setCurrentLogLevel(LogLevel::Warning);
*qLog(LogLevel::Debug) << "this will be filtered" << yourQMap;
*qLog(LogLevel::Critical) << "not filtered" << yourQString;

As you'd be dealing with globals, carefully consider memory management issues.当您要处理全局变量时,请仔细考虑 memory 管理问题。

If you follow the method in that link, ALL messages of the application output with qCritical(), qDebug(), qFatal() and qWarning() will flow into your handler.如果您遵循该链接中的方法,则应用程序 output 的所有消息(带有 qCritical()、qDebug()、qFatal() 和 qWarning())都将流入您的处理程序。

So be careful!所以要小心! You may get not only your library's trace messages but the entire QT framework's messages.您不仅可以获得库的跟踪消息,还可以获得整个QT 框架的消息。 I guess this is not what you really want.我想这不是你真正想要的。

Instead of this as a simple solution define a global * ofstream * in your library and use it only within your library.而不是作为一个简单的解决方案在您的库中定义一个全局* ofstream * 并仅在您的库中使用它。

whenever you write a library in c++ or c, it is best practice to declare all your methods in ah file and define the methods/classes in a.cpp/.c file.每当您在 c++ 或 c 中编写库时,最好在 ah 文件中声明所有方法并在 a.cpp/.Z4A8A08F09D37B737933649038408B 文件中定义方法/类。 This serves 2 purposes.这有两个目的。

  1. The.h file needs to be used to compile a 3rd party application that is using your library, and the library itself is used at link time. .h 文件需要用于编译使用您的库的第 3 方应用程序,并且库本身在链接时使用。
  2. The developer who is using your library can use the.h file as a reference to your library since it contains all the declarations.使用您的库的开发人员可以使用 .h 文件作为对您的库的引用,因为它包含所有声明。

So,yes, you need to declare methods in ah file and have other classes include logger.h .所以,是的,您需要在 ah 文件中声明方法并让其他类包括logger.h

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

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