[英]How can I know if C++ compiler make thread-safe static object code?
[英]Need to know how to check if the inputted string has terminated within a thread-safe logger in C++
我对此很陌生,如果我的问题不清楚,我深表歉意。
我已经在C ++中创建了一个线程安全记录器。 该记录器将在大型程序中使用,并将在多个地方调用。 我使用的是单例,因此记录器只有一个实例。 该记录器输出到文件和控制台。 它的行为类似于cout; 它从另一个文件中获取一个字符串(必要时将其连接),将peices存储在缓冲区中,直到完成字符串,然后使用cout输出。 该字符串被存储为const char *。 现在,互斥锁被锁定在一个功能中,而在另一个功能中被解锁(这是我的问题所在),这会使endl运算符超载。
我的问题是,仅当用户在调用记录器的其他文件中写入endl时,此功能(互斥锁已解锁)才起作用。 我需要它成为一个通用的实用程序,它不会依赖于用户编写的内容,因为用户可能不使用endl或使用它的次数可能过多。 现在,我的记录器需要一些方法来识别字符串(来自另一个文件)何时完成,以便可以清空缓冲区。 目前,endl就像一个关键字,我需要一些方法来使其在没有任何关键字的情况下工作。
我最初以为我可以找到一些方法来检查字符串中的“ \\ 0”终止字符,然后使用该检查来知道字符串已完成,然后清空缓冲区。 但是,当我这样做时,我会越界错误。
感谢您的时间
我不太确定会遇到这种情况,但是听起来您想要代理:
class LogSingleton
{
public:
LogSingleton& instance() { /* ... */ }
void lock(); // lock mutex
void unlock(); // unlock mutex
template <typename T>
friend LogSingleton& operator<<(LogSingleton& pLog, const T& pX)
{
// needs to be locked first
assert(is_locked());
/* output pX however */
return pLog;
}
};
class LogProxy
{
public:
LogProxy()
{
// manage lock in proxy
LogSingleton::instance().lock();
}
~LogProxy()
{
LogSingleton::instance().unlock();
}
};
// forward input into the proxy to the log, knowing it's locked
template <typename T>
LogProxy& operator<<(LogProxy& pProxy, const T& pX)
{
LogSingleton::instance() << pX;
return pProxy;
}
// now expose proxy
typedef LogProxy log;
您可以这样做:
log() << "its locked now" << "and the temporary will die" << "here ->";
锁定在构造函数和析构函数中完成,并且在最后调用析构函数。
正如Tony正确指出的那样,这会不必要地长时间保持锁。 只有将“最终”输出输出到LogSingleton
时才需要锁定。 想象一下:
log() << "this next function takes 5 minutes"
<< my_utterly_crappy_function() << "ouch";
什么都没有记录,但互斥锁已锁定很长时间了。 最好将输出缓冲起来,然后一次全部输出:
class LogProxy
{
public:
~LogProxy()
{
// manage lock in proxy
LogSingleton::instance().lock();
// no-throw, or wrap mutex use in a scoped-lock
LogSingleton::instance() << mBuffer.rdbuf();
LogSingleton::instance().unlock();
}
// buffer output
template <typename T>
friend LogProxy& operator<<(LogProxy& pProxy, const T& pX)
{
mBuffer << pX;
return pProxy;
}
private:
std::ostringstream mBuffer;
};
现在,在准备好输出缓冲区之前,不会获取任何锁。
通常,在一个功能中具有互斥锁并在另一个功能中解锁是一个坏主意。 它应该在相同的功能中被锁定和解锁。
我创建了类似的东西,通常我制作了一个名为Error的C ++类。
这样,用户可以创建一个Error对象,并且该Error对象可以处理所有终止操作。 然后,错误对象被发送到ErrorLogger的队列,并且ErrorLogger队列为空时,错误记录器终止。 然后,您不必担心互斥锁,因为ErrorLogger有时间处理队列之外的内容。
检查https://web.archive.org/web/1/http://articles.techrepublic%2ecom%2ecom/5100-10878_11-5072104.html
这个想法是创建线程本地的“代理”,该代理将调用实际的线程安全日志记录功能。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.