发送消息后,套接字神秘地从哈希图中删除
Posted
技术标签:
【中文标题】发送消息后,套接字神秘地从哈希图中删除【英文标题】:Socket gets mysteriously removed from hashmap after sending a message 【发布时间】:2021-04-19 07:21:16 【问题描述】:所以我是 Java 套接字的新手,刚刚开始使用它们。问题是:我有一个客户端和一个服务器应用程序。客户端想要向另一个客户端发送一些消息。这些消息将到达服务器,并在服务器端将它们放入队列中,并每 2 秒检查一次目标客户端(套接字)是否还活着。如果是这样,那么我将清空队列并将每条消息发送给特定的客户端。否则,消息将存储在服务器应用程序中,直到目标套接字处于活动状态。
但是,主要问题是在服务器将第一条消息传递到套接字后,客户端(目标)套接字消失了。我尝试将这些套接字存储在哈希图中。因此,在发送了第一条消息后,哈希映射会以某种方式变空。而且我无法传递其余的消息。
我提供一些代码:
public class Server
public static volatile HashMap<Socket,String> clients;
public Server()
clients = new HashMap<>();
public void start()
try(ServerSocket serverSocket = new ServerSocket(5000))
while(true)
Socket socket = serverSocket.accept();
System.out.println("Client connected");
new clientHandler(socket).start();
catch(IOException e)
e.printStackTrace();
public class clientHandler extends Thread
private Socket socket;
private Socket sendSocket;
private Timer timer;
private Queue<String> msgStack;
private String socketName = "";
public clientHandler(Socket socket)
this.socket = socket;
msgStack = new PriorityQueue<>();
@Override
public void run()
try
BufferedReader input = new BufferedReader(new InputStreamReader(socket.getInputStream()));
PrintWriter output = new PrintWriter(socket.getOutputStream(),true);
while(true)
String line = input.readLine();
if(!line.contains("|") && line != null)
if(!isClientAdded(line))
Server.clients.put(socket, line);
else
System.out.println(line);
String[] msg = line.split("\\|");
String fromUser = msg[0];
String toUser = msg[1];
String subject = msg[2];
String msgText = msg[3];
if(isClientAdded(toUser))
sendMsg(line);
if(timer.isRunning())
timer.stop();
else
msgStack.add(line);
timer = new Timer(2000, new ActionListener()
@Override
public void actionPerformed(ActionEvent e)
System.out.println(msgStack+" "+msgStack.size());
if(isClientAdded(toUser))
if(!msgStack.isEmpty())
sendMsg(msgStack.poll());
System.out.println("MSg: "+fromUser+" "+toUser+" "+subject+" "+msgText);
if(msgStack.isEmpty())
timer.stop();
);
timer.start();
catch (SocketException ex)
ex.printStackTrace();
Server.clients.remove(socket);
catch (IOException ex)
ex.printStackTrace();
public boolean isClientAdded(String clientName)
Iterator it = Server.clients.entrySet().iterator();
while (it.hasNext())
Map.Entry pair = (Map.Entry)it.next();
if(clientName.equals(pair.getValue()+""))
return true;
it.remove();
return false;
public void sendMsg(String send)
String[] msg = send.split("\\|");
String fromUser = msg[0];
String toUser = msg[1];
String subject = msg[2];
String msgText = msg[3];
Iterator it = Server.clients.entrySet().iterator();
while (it.hasNext())
Map.Entry pair = (Map.Entry)it.next();
if((pair.getValue()+"").equals(toUser))
try
socket = ((Socket)pair.getKey());
PrintWriter output = new PrintWriter(socket.getOutputStream(),true);
output.println(fromUser+"|"+subject+"|"+msg);
catch (IOException ex)
ex.printStackTrace();
it.remove();
我从其对“名称”中识别出每个套接字。这就是我如何知道我应该发送消息的套接字。
【问题讨论】:
你在 isClientAdded 的 hashmap 中明确删除了条目,为什么? 【参考方案1】:是的,我遇到了问题,感谢评论部分中的 Rocco。问题是 it.remove() 部分。我从另一个项目复制/粘贴了这个 hashmap 迭代代码,因为在我的记忆中这个 hashmap 迭代器只是简单的迭代,但它最后有一个 it.remove(),我不记得了。
【讨论】:
以上是关于发送消息后,套接字神秘地从哈希图中删除的主要内容,如果未能解决你的问题,请参考以下文章
发送几条消息后,WebSocket readyState 停留在 0