我开发了一个单一的服务器/多个客户端TCP应用程序。
客户端由x个线程组成,每个线程对自己的数据进行处理,然后通过TCP套接字将数据发送到服务器进行显示。
服务器基本上是一个有窗口的GUI。 服务器从客户端接收数据并显示它。
现在的问题是,因为客户端内部有40个线程,每个线程都想发送数据,我怎样才能使用一个连接的套接字来实现呢?
隐式调用时如何使用RTLD_DEEPBIND?
从C#中的串行端口接收数据的问题?
访问()有什么问题?
为什么在不同的堆栈使用情况下,每次运行都会发生堆栈溢出而不是固定的数量?
我的build议:
我的方法是在要发送数据的40个线程中的每个线程中都创build一个数据结构。 然后创build一个单独的发送线程与客户端上的一个连接的套接字。 该线程将从第一个线程的数据结构中读取数据,通过套接字发送数据,然后从第二个线程读取数据等等。
困惑:
但我不确定这是如何实施的,因为我对这一切都是陌生的? :(如果一个线程正在写入数据结构,并且发送线程尝试同时读取这些数据,那么我就熟悉互斥锁,临界区等,但是对于我的简单应用来说,这听起来太复杂了。
除了我自己的build议之外,还有其他任何build议/意见。 如果你认为我自己的方法是正确的,那么请帮我解决我上面提到的困惑。
非常感谢:)
编辑:
我可以把我的计时器上的发送线程和特定的时间后,发送线程暂停线程#1(以便它可以访问其数据结构,没有任何同步问题),从数据结构中读取数据,通过TCP Socket发送,恢复线程#1,然后暂停线程#2,从其数据结构中读取数据,通过tcp Socket发送数据,然后恢复线程#2,等等。
在哪里可以在系统上安装SDK DLL,以便可以通过需要它们的应用程序find它们
在C#和Windows中限制评估软件的启动或运行时间
是否有strsep()的窗口变体
Linux与Windows 7(VM)C ++执行速度
为什么不可以使用ioremap,然后remap_pfn_range?
一个常见的方法是有一个线程专用于发送数据。 其他线程将他们的数据发布到共享容器(列表,deque等)中,并向发送者线程发送数据可用的信号。 发送者然后醒来并处理任何可用的数据。
编辑:
其要点如下:
HANDLE data_available_event; // manual reset event; set when queue has data,clear when queue is empty CRITICAL_SECTION cs; // protect access to data queue std::deque<std::string> data_to_send; WorkerThread() { while(do_work) { std::string data = generate_data() EnterCriticalSection(&cs); data_to_send.push_back(data); SetEvent(data_available_event); // signal sender thread that data is available LeaveCriticalSection(&cs); } } SenderThread() { while(do_work) { WaitForSingleObject(data_available_event); EnterCriticalSection(&cs); std::string data = data_to_send.front(); data_to_send.pop_front(); if(data_to_send.empty()) { ResetEvent(data_available_event); // queue is empty; reset event and wait until more data is available } LeaveCriticalSection(&cs); send_data(data); } }
这当然假设数据可以以任何顺序发送。 我使用字符串仅用于说明目的; 您可能需要某种自定义对象来知道如何序列化它所保存的数据。
挂起线程#1,以便您可以访问其数据strcuture不会避免同步问题。 当你挂起它时,线程#1可能正在更新数据,所以套接字线程获得了旧数据的一部分,是新数据的一部分。 这是数据损坏。
您需要共享的数据结构,如FIFO队列。 工作线程添加到队列中,套接字线程从队列中移除最旧的项目。 除非您实施无锁队列,否则对共享队列的所有访问都必须使用关键部分进行保护。 (一个循环缓冲区)
根据您的应用程序需求,如果您实现此队列,则可能根本不需要套接字线程。 只要在显示线程中进行出列。
有几个方法来实现它; 卢克的想法遭受了仍然会造成数据腐败的竞争状况
您避免使用UDP而不是TCP作为传输协议。 如果你不介意丢失偶尔的数据包(这对显示快速变化的数据是可以的),那么这将是一个不错的选择。 对于确切的历史记录无关紧要的数据确保实时更新是一件很棒的事情(在绘制图形的过程中,在相对平滑的曲线中缺少一个点);
如果数据包很小并且代表一个流,那么UDP是一个很好的选择。 如果在不同的系统上有多个发送者在一个屏幕上显示,它的好处就会增加。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 [email protected] 举报,一经查实,本站将立刻删除。