【发布时间】:2018-08-14 20:26:16
【问题描述】:
我有一个客户端套接字列表,通常大小约为 2000。这些客户端是动态的,它们来来去去。
我有一个ExecutorService,它有一个由 32 个线程组成的固定线程池来处理这些线程。这个执行器服务负责解码和发送要发送给这 2000 个客户端的消息。
我想防止执行器服务的两个(或更多)线程同时处理同一个客户端。
一种方法可能是引入另一个簿记线程(所以我最终得到了 32 + 1 个线程),它负责在对应于同一客户端的上一条消息完成时调用 ExecutorService.submit(mesage)。但我不确定这是否会引入瓶颈,这意味着这个新引入的 bookkeeping 线程 无法跟上提交消息的速度。
理想情况下,我不想提前为一组客户端预分配线程,因为消息负载在客户端之间分布不均。也是事先不知道的。
有什么方法可以解决这个问题?它们是由java.util.concurrent 功能提供的吗?
更新
这是一个简短的总结,因为 cmets 指出存在一些误解:
我不希望每个客户端有一个线程,因为我最终会得到 2000 个线程。
理想情况下,我不想为一组客户端预先分配一个线程,因为消息速率不是在所有客户端之间均匀分布,而且事先不知道。
必须保留消息顺序。
我认为线程
A正在等待线程B并不好,因为B已经在向同一个客户端发送消息。换句话说,始终只有一个线程在处理一个客户端。
【问题讨论】:
-
“我想防止执行器服务的两个(或多个)线程同时处理同一个客户端。”不明白这个要求。您是否会同时为同一个客户提供 2 个工作?为什么会有这样的问题?
-
我认为他想序列化来自同一来源的处理请求。不知道为什么
-
客户端socket只能被一个线程同时使用,不是线程安全的。此外,客户端的消息必须按正确的顺序发送。
-
不是序列化线程,而是序列化套接字写入。
-
这不是最理想的吗,因为许多线程可能正在等待保护一个线程持有的套接字的锁?另外,我们如何在这种方法中保留消息顺序?
标签: java multithreading java.util.concurrent