我正在编写一个服务器(主要用于Windows,但如果我可以保持它多平台,它会很酷),我只是使用一个正常的控制台窗口。但是,我希望服务器能够执行诸如text_to_say_here或kick playername等命令。如何获得异步输入/输出?我已经尝试了一些正常的printf()和gets_s,但是导致了一些非常奇怪的东西。C++同时输入和输出到控制台窗口
我意味着什么这个1
感谢等。
我正在编写一个服务器(主要用于Windows,但如果我可以保持它多平台,它会很酷),我只是使用一个正常的控制台窗口。但是,我希望服务器能够执行诸如text_to_say_here或kick playername等命令。如何获得异步输入/输出?我已经尝试了一些正常的printf()和gets_s,但是导致了一些非常奇怪的东西。C++同时输入和输出到控制台窗口
我意味着什么这个1
感谢等。
您可以尝试将输入和输出放在单独的线程上。我不太清楚为什么你想这样做,但线程应该做这个工作。 :)
您可以使用线程模拟异步I/O,但更重要的是,你必须共享两个读之间的互斥/为了避免与线程踩着其他任何问题,写线程线程,并在另一个线程的输出之上写入控制台。换句话说,std::cout
,std::cin
,fprintf()
等不是多线程安全的,因此,在另一个读或写已经发生的两个操作之间发生读或写操作时,您将得到一个不可预测的交错模式。您可能很容易就会在写入过程中发生读取操作,此外,当您在控制台上键入输入时,另一个写入线程可能会开始在控制台上写入内容,从而导致视觉混乱正在尝试输入。
为了正确管理您的异步读写线程,最好设置两个类,一个用于读取,另一个用于写入。在每个类中,设置一个消息队列,该消息队列将存储消息(最有可能为std::string
),供主线程在读取线程的情况下检索,并且主线程在写入线程的情况下推送消息。您可能还需要制作一个特殊版本的读取线程,可以打印提示信息,主要线程会将消息推入到其消息队列中,在从stdin
或std::cin
读取数据之前将打印提示。这两个类然后将共享一个共同的互斥或信号量以防止I/O的不可预测的交错。通过在任何iostream
调用(之后解锁)之前锁定普通互斥锁,将避免任何不可预知的I/O交错。每个线程还会添加另一个互斥量,该互斥量对于每个线程都是唯一的,可用于维护对类的内部消息队列的访问权限。最后,您可以将每个类中的消息队列实现为std::queue<std::string>
。
如果你想让你的程序尽可能跨平台,我会建议用Boost :: threads或者使用新的C++ 0x std :: threads库来实现它。
如果您抛弃控制台窗口并使用TCP连接进行命令和控制,您的服务器将更容易保持多平台,并且也更简单且更灵活。
快速代码利用C++ 11个功能(即跨平台)
#include <atomic>
#include <thread>
#include <iostream>
void ReadCin(std::atomic<bool>& run)
{
std::string buffer;
while (run.load())
{
std::cin >> buffer;
if (buffer == "Quit")
{
run.store(false);
}
}
}
int main()
{
std::atomic<bool> run(true);
std::thread cinThread(ReadCin, std::ref(run));
while (run.load())
{
// main loop
}
run.store(false);
cinThread.join();
return 0;
}
什么 “奇怪的东西”? – NPE
[无耻的插件](https://github.com/louisdx/schlagwetter):-) –
只是模拟一个中断处理程序。我猜你会好起来的。 –