Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/sockets/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 由于我想让多个用户制作一个聊天程序,如何从这些代码中添加线程?_Java_Sockets_Networking_Network Programming_Client Server - Fatal编程技术网

Java 由于我想让多个用户制作一个聊天程序,如何从这些代码中添加线程?

Java 由于我想让多个用户制作一个聊天程序,如何从这些代码中添加线程?,java,sockets,networking,network-programming,client-server,Java,Sockets,Networking,Network Programming,Client Server,java-完成所有客户端的工作 package sampleclient; import java.io.*; import java.net.*; import java.awt.*; import java.awt.event.*; import javax.swing.*; public class SampleClient extends JFrame{ private JTextField userText; private JTextArea chatWindow; priva

java-完成所有客户端的工作

package sampleclient;

import java.io.*;
import java.net.*;
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;

public class SampleClient extends JFrame{

private JTextField userText;
private JTextArea chatWindow;
private ObjectOutputStream user;
private ObjectOutputStream output;
private ObjectInputStream input; //from the server
private String message = "";
private String serverIP;
private Socket connection;
private String name;
private JTextArea contacts;
private PrintWriter toS;

//constructor
public SampleClient(String host, String username){
    super("Client");
    serverIP = host;
    name = username;
    userText = new JTextField();
    userText.setEditable(false); //not allowed to type while no one is connected
    userText.addActionListener(
        new ActionListener(){
            public void actionPerformed(ActionEvent event){
                sendMessage(event.getActionCommand());
                userText.setText("");

            }

        }
        );
    add(userText, BorderLayout.SOUTH);
    contacts = new JTextArea();
    chatWindow = new JTextArea();
    add(new JScrollPane(contacts), BorderLayout.EAST); //scroll
    contacts.append("   ONLINE CONTACTS   \n");
    add(new JScrollPane(chatWindow), BorderLayout.CENTER); //scroll
    setSize(300, 150);
    setVisible(true);
}

//connect to server
public void startRunning(){
    try {

        connectServer();
        setupStreams();
        whileChatting();

    }catch(EOFException eofException){
        showMessage("\n Client terminated connection");
    }catch (IOException ioException){
        ioException.printStackTrace();
    }finally{
        closeAll();
    }
}

//connectServer
private void connectServer() throws IOException{
    showMessage("Attempting connection... \n");
    connection = new Socket(InetAddress.getByName(serverIP), 6789); //passes to an IP Adrdress and Port Number
    showMessage("Connected to:" + connection.getInetAddress().getHostName()); //prompt
    toS = new PrintWriter(connection.getOutputStream(), true);
    toS.println(name);

}

//set up streams for sending and receive the messages
private void setupStreams()throws IOException{
    output = new ObjectOutputStream(connection.getOutputStream());
    output.flush();
    input = new ObjectInputStream(connection.getInputStream()); //receive messages
    showMessage("\n Streams are connected");

}

//actual chat
private void whileChatting()throws IOException{
    ableToType(true);
    do{
        try{
            message = (String) input.readObject();
            showMessage("\n" +message);
        }catch(ClassNotFoundException classNotFoundException){
            showMessage("\n ERROR!");
        }
    }while(!message.equals("SERVER - END"));
}

//close sockets and streams
private void closeAll(){
    showMessage("\n Closing connections..");
    ableToType(false);
    try{
        output.close();
        input.close();
        connection.close();
    }catch(IOException ioException){
        ioException.printStackTrace();
    }
}

//send messages to server
private void sendMessage(String message){
    try{
        System.out.println(name);
        output.writeObject( "\n" + name + ": " + message);
        output.flush(); //push bytes
        showMessage("\n" + name + ": " + message);

    }catch(IOException ioException){
        chatWindow.append("ERROR!");

    }
}

//Update chatWindow
private void showMessage(final String m){
    SwingUtilities.invokeLater(
            new Runnable(){
                public void run(){
                    chatWindow.append(m); //appear at the end of the conversation

                }
            }
    );

}

//permission to type to for user
private void ableToType(final boolean tof){
    SwingUtilities.invokeLater(
            new Runnable(){
                public void run(){
                    userText.setEditable(tof);
                }
            }
    );
}
} 
clientTest.java

    package sampleclient;
    import javax.swing.*;

    public class ClientTest {

        public String userName;
        private static JFrame frame = new JFrame("Messenger");

            private static String getUsername() {
            return JOptionPane.showInputDialog(
                frame,
                "Enter Username:",
                "Instant Messenger",
                JOptionPane.QUESTION_MESSAGE);
        }

        public static void main(String[] args){

            String username = getUsername();//getting username
            SampleClient client;                     
            client = new SampleClient("10.0.1.4", username); //localhost

            client.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            client.startRunning();
        }

    }
java—完成所有服务器的工作

        package sampleserver;

        import java.io.*;
        import java.net.*;
        import java.awt.*;
        import java.awt.event.*;
        import javax.swing.*;
        import java.util.*;
        import java.lang.Object.*;


        public class SampleServer extends JFrame{

            private JTextField userText; //message variable area
            private JTextArea chatWindow; //display the conversation
            private ObjectOutputStream output; //output stream->flows from my computer to the other computer
            private ObjectInputStream input; //input stream->receive stuff
            private ObjectInputStream name; //input stream->receive stuff
            private ServerSocket server; //server variable
            private Socket connection; //socket variable
            private Vector<String> users;
            private Vector<String> ips;
            private JTextArea conList;
            private PrintWriter p;
            private BufferedReader fromC;

            //constructor
            public SampleServer(){
                super("Instant Messenger");
                userText = new JTextField(); //text field
                userText.setEditable(false); //not allowed to type anything if there are no online
                userText.addActionListener(
                        new ActionListener(){
                            public void actionPerformed (ActionEvent event){
                                sendMessage(event.getActionCommand()); //sends the message
                                userText.setText("");
                            }
                        }
                );
                add(userText, BorderLayout.SOUTH);
                users = new Vector();
                ips = new Vector();
                chatWindow = new JTextArea();
                conList = new JTextArea();
                conList.setEditable(false);
                add(new JScrollPane(chatWindow));
                add(new JScrollPane(conList), BorderLayout.EAST);
                conList.append("   ONLINE USERS    \n");
                setSize(300, 150);
                setVisible(true);
            }

           //set up and run the server
           public void startRunning(){
               try {
                   server = new ServerSocket(6789, 100); //port number and only 100 can connect to the server
                   while(true){
                       try{
                           //connect and have conversation to other client
                           waitForConnection(); //waiting method
                           setupStreams(); //set up output and input stream
                           whileChatting(); //actual chat

                       }catch(EOFException eofException){
                           showMessage("\n Server ended the connection!");
                       }finally {
                           closeAll();
                       }
                   }

               }catch(IOException ioException){
                   ioException.printStackTrace();
               }
           }

           //wait for connection, then display connection information
           private void waitForConnection() throws IOException{
               showMessage("Waiting for someone to connect...\n");
               connection = server.accept(); //once someone asked for connection, accepts this
               //showMessage("Now connected to "+connection.getInetAddress().getHostName()); //converts the ip address to string

               ips.add(connection.getInetAddress().getHostName()); // adds ip address of client to ips vector

               fromC = new BufferedReader(new InputStreamReader(connection.getInputStream())); // gets what client sent through printwriter - username
               String s = new String(fromC.readLine()); // saves as string
               users.add(s); // saves username of client to users vector
               String con = (connection.getInetAddress().getHostName());
               showMessage(s + " / " + con + " has connected.");

               Iterator c = users.iterator(); // username iterator
               Iterator b = ips.iterator(); // ip address iterator

               while(c.hasNext()) {

                   String d = (c.next()).toString(); // gets next element in users vector
                   String e = (b.next().toString()); // gets next element in ips vector
                   conList.append(d + "\n"); // displays username in online users list
                   conList.append("(" + e + ")\n\n"); // displays ip in online users list
               }

           }

           //get stream to send and receive data
           private void setupStreams()throws IOException{
               output = new ObjectOutputStream(connection.getOutputStream()); //computer who we communicate to
               output.flush(); //bytes of information that is send to other person (leftover)
               input = new ObjectInputStream(connection.getInputStream()); //receive messages
               showMessage("\n Streams are now setup! \n");



           }

           //actual chat conversation
           private void whileChatting() throws IOException{
               String message = "You are now connected!";
               sendMessage(message); 
               ableToType(true);
               do{
                   try{
                       message = (String) input.readObject(); //views it as an object and make sure it's a string
                       showMessage("\n" + message);
                   }catch(ClassNotFoundException classNotFoundException){
                       showMessage("\nError!");
                   }
               }while(!message.equals("CLIENT - END"));

           }

           //close streams and sockets 
           private void closeAll(){
               showMessage("\n Closing connection... \n");
               ableToType(false);
               try{
                   output.close();
                   input.close();
                   connection.close();
               }catch(IOException ioException){
                   ioException.printStackTrace();

               }
           }

           //send message to other computer
           private void sendMessage(String message){
               try{
                   output.writeObject("SERVER - " +message); //sends the mesage to the output stream
                   output.flush(); //push extra bytes to user
                   showMessage("\n SERVER - " + message);
               }catch(IOException ioException){
                   chatWindow.append("\n ERROR!"); //put in the chat area

               }

           }

           //updates chatWindow
           private void showMessage(final String text){
               SwingUtilities.invokeLater( //updats GUI or threads
                       new Runnable(){
                           public void run(){
                               chatWindow.append(text); //add string at the end of the chatWindow
                           }
                       }
               );

           }

           //allow user to type
           private void ableToType(final boolean tof){
                SwingUtilities.invokeLater( //updats GUI or threads
                       new Runnable(){
                           public void run(){
                              userText.setEditable(tof); //updates the GUI
                           }
                       }
               );
           }

        }

问题是我们必须做一个客户端程序,我们做的是有两台笔记本电脑,一台用于打开客户端和服务器,另一台仅用于客户端。两台笔记本电脑已成功连接(客户端-服务器),但装有服务器的笔记本电脑的客户端无法连接到聊天室。但是,如果第二台笔记本电脑的客户端关闭,第一台笔记本电脑可以连接到其服务器。请帮助?

问题是您只为一台计算机编程了聊天应用程序,因为它不会为每个客户端创建新的
线程,并进入while循环,直到客户端断开连接

//connect and have conversation to other client
waitForConnection(); //waiting method
setupStreams(); //set up output and input stream
whileChatting(); //actual chat //The problem is here, this should have been in a new Thread
将SampleServer.java更改为:

package sampleserver;

import java.io.*;
import java.net.*;
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import java.util.*;
import java.lang.Object.*;


public class SampleServer{

    private ObjectOutputStream output; //output stream->flows from my computer to the other computer
    private ObjectInputStream input; //input stream->receive stuff
    private ObjectInputStream name; //input stream->receive stuff
    private Socket connection; //socket variable
    private String user;
    private String ip;
    private PrintWriter p;
    private BufferedReader fromC;
    private serverTest server; //Saves the server test to append messages.

    //constructor
    public SampleServer(Socket c, String username, String userip, serverTest t){  //EDITED!!
        connection = c;
        server = t;
        ip= userip;
        user= username;             
        setupStreams(); //set up output and input stream
    }

    public void run() //This method gets called when Thread starts running
    {
        whileChatting();
        closeAll();
    }

   //get stream to send and receive data
   private void setupStreams(){
       try{
       output = new ObjectOutputStream(connection.getOutputStream()); //computer who we communicate to
       output.flush(); //bytes of information that is send to other person (leftover)
       input = new ObjectInputStream(connection.getInputStream()); //receive messages
       showMessage("\n Streams are now setup! \n");
       }catch(IOException ioException){
           ioException.printStackTrace();

       }
   }

   //actual chat conversation
   private void whileChatting(){
       String message = "You are now connected!";
       sendMessage(message); 
       do{
           try{
               message = (String) input.readObject(); //views it as an object and make sure it's a string
               showMessage("\n" + message);
           }catch(Exception e){
               //showMessage("\nError!");
           }
       }while(!message.equals("CLIENT - END"));

   }

   //close streams and sockets 
   public void closeAll(){
       showMessage("\n Closing connection... \n");
       try{
           output.close();
           input.close();
           connection.close();
       }catch(IOException ioException){
           ioException.printStackTrace();

       }
   }

   //send message to other computer
   public void sendMessage(String message){
       try{
           output.writeObject("SERVER - " +message); //sends the mesage to the output stream
           output.flush(); //push extra bytes to user
       }catch(IOException ioException){
           showMessage("\n ERROR!"); //put in the chat area

       }

   }

   //updates chatWindow
   private void showMessage(String text){
       server.showMessage(text);
   }
}
并将serverTest.java更改为:

    package sampleserver;

import java.io.*;
import java.net.*;
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import java.util.*;
import java.lang.Object.*;

public class serverTest extends JFrame {
    private JTextField userText; //message variable area
    private JTextArea chatWindow; //display the conversation
    private ServerSocket server; //server variable
    private Vector<String> users;
    private Vector<String> ips;
    private JTextArea conList;
    private ArrayList<SampleServer> connections = new ArrayList<SampleServer>();

    public static void main(String[] args){
        new serverTest();
    }

    public serverTest()
    {
        super("Instant Messenger");
        userText = new JTextField(); //text field
        userText.addActionListener(
                new ActionListener(){
                    public void actionPerformed (ActionEvent event){
                        sendMessage(event.getActionCommand()); //sends the message
                        userText.setText("");
                    }
                }
        );
        add(userText, BorderLayout.SOUTH);
        users = new Vector();
        ips = new Vector();
        chatWindow = new JTextArea();
        conList = new JTextArea();
        conList.setEditable(false);
        add(new JScrollPane(chatWindow));
        add(new JScrollPane(conList), BorderLayout.EAST);
        conList.append("   ONLINE USERS    \n");
        setSize(300, 150);
        setDefaultCloseOperation(EXIT_ON_CLOSE);
        setVisible(true);

       try {
           server = new ServerSocket(6789, 100); //port number and only 100 can connect to the server
           while(true){
               try{
                    showMessage("Waiting for someone to connect...\n");
                    Socket connection = server.accept(); //once someone asked for connection, accepts this
                    //showMessage("Now connected to "+connection.getInetAddress().getHostName()); //converts the ip address to string

                    ips.add(connection.getInetAddress().getHostName()); // adds ip address of client to ips vector

                    BufferedReader fromC = new BufferedReader(new InputStreamReader(connection.getInputStream())); // gets what client sent through printwriter - username
                    String s = new String(fromC.readLine()); // saves as string
                    users.add(s); // saves username of client to users vector
                    String con = (connection.getInetAddress().getHostName());
                    showMessage(s + " / " + con + " has connected.");

                    Iterator c = users.iterator(); // username iterator
                    Iterator b = ips.iterator(); // ip address iterator

                    conList.setText("");

                    while(c.hasNext()) {

                        String d = (c.next()).toString(); // gets next element in users vector
                        String e = (b.next().toString()); // gets next element in ips vector
                        conList.append(d + "\n"); // displays username in online users list
                        conList.append("(" + e + ")\n\n"); // displays ip in online users list
                    }
                    final SampleServer se = new SampleServer(connection, s, con, this);
                    Thread t = new Thread(new Runnable(){
                        public void run()
                        {
                            se.run();
                        }
                    });
                    connections.add(se);
               }catch(EOFException eofException){
                   showMessage("\n Server ended the connection!");
               }
           }

       }catch(IOException ioException){
           ioException.printStackTrace();
       }
    }

    public void closeAll()
    {
        while (!connections.isEmpty())
        {
            connections.get(0).closeAll();
            connections.remove(0);
        }
    }

    public void sendMessage(String text)
    {
                showMessage("\n SERVER - " + text);
        for (SampleServer s : connections)
        {
            s.sendMessage(text);
        }
    }

    public void showMessage(final String text)
    {
       SwingUtilities.invokeLater( //updats GUI or threads
               new Runnable(){
                   public void run(){
                       chatWindow.append(text); //add string at the end of the chatWindow
                   }
               }
       );
    }
}
package-sampleserver;
导入java.io.*;
导入java.net。*;
导入java.awt.*;
导入java.awt.event.*;
导入javax.swing.*;
导入java.util.*;
导入java.lang.Object.*;
公共类serverTest扩展了JFrame{
私有JTextField userText;//消息变量区域
私有JTextArea聊天窗口;//显示对话
私有服务器套接字服务器;//服务器变量
专用矢量用户;
专用载体IP;
私人区域控制列表;
私有ArrayList连接=新建ArrayList();
公共静态void main(字符串[]args){
新服务器测试();
}
公共服务器测试()
{
超级(“即时通讯”);
userText=newjtextfield();//文本字段
userText.addActionListener(
新建ActionListener(){
已执行的公共无效操作(操作事件){
sendMessage(event.getActionCommand());//发送消息
userText.setText(“”);
}
}
);
添加(userText,BorderLayout.SOUTH);
用户=新向量();
ips=新向量();
chatWindow=新的JTextArea();
conList=新的JTextArea();
conList.setEditable(false);
添加(新的JScrollPane(聊天窗口));
添加(新的JScrollPane(conList),BorderLayout.EAST);
conList.append(“在线用户”\n);
设置大小(300150);
setDefaultCloseOperation(关闭时退出);
setVisible(真);
试一试{
server=newserversocket(6789100);//端口号,只有100可以连接到服务器
while(true){
试一试{
showMessage(“正在等待某人连接…\n”);
Socket connection=server.accept();//一旦有人请求连接,就接受它
//showMessage(“现在连接到”+connection.getInetAddress().getHostName());//将ip地址转换为字符串
add(connection.getInetAddress().getHostName());//将客户端的ip地址添加到ips向量
BufferedReader fromC=new BufferedReader(new InputStreamReader(connection.getInputStream());//获取客户端通过printwriter发送的内容-用户名
String s=新字符串(fromC.readLine());//另存为字符串
users.add(s);//将客户端的用户名保存到用户向量
字符串con=(connection.getInetAddress().getHostName());
showMessage(s+“/”+con+“已连接”);
迭代器c=users.Iterator();//用户名迭代器
迭代器b=ips.Iterator();//ip地址迭代器
conList.setText(“”);
while(c.hasNext()){
字符串d=(c.next()).toString();//获取用户向量中的下一个元素
字符串e=(b.next().toString());//获取ips向量中的下一个元素
conList.append(d+“\n”);//在联机用户列表中显示用户名
conList.append(“(+e+”)\n\n”);//在联机用户列表中显示ip
}
final SampleServer se=新的SampleServer(连接,s,con,this);
线程t=新线程(新的可运行线程(){
公开募捐
{
se.run();
}
});
连接。添加(se);
}捕获(EOFEException EOFEException){
showMessage(“\n服务器已结束连接!”);
}
}
}捕获(IOException IOException){
ioException.printStackTrace();
}
}
公共空间关闭所有()
{
而(!connections.isEmpty())
{
connections.get(0.closeAll();
连接。移除(0);
}
}
公共无效发送消息(字符串文本)
{
showMessage(“\n服务器-”+文本);
用于(示例服务器:连接)
{
s、 发送消息(文本);
}
}
公共void showMessage(最终字符串文本)
{
SwingUtilities.invokeLater(//更新GUI或线程
新的Runnable(){
公开募捐{
append(text);//在聊天窗口的末尾添加字符串
}
}
);
}
}
在这里,我将GUI代码移到了主类,还将serversocket移到了主类,并使SampleServer只有一个用户。当它收到消息时,它会将其添加到GUI中。
只有服务器可以发送消息,而服务器不向客户端发送用户列表。

是什么机制使其能够在多台计算机上工作?@Thufir原始代码没有为每个客户端创建新的
线程,因此一次只能为一个客户端服务,因为当客户端连接时,代码进入
循环,直到客户端退出
    package sampleserver;

import java.io.*;
import java.net.*;
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import java.util.*;
import java.lang.Object.*;

public class serverTest extends JFrame {
    private JTextField userText; //message variable area
    private JTextArea chatWindow; //display the conversation
    private ServerSocket server; //server variable
    private Vector<String> users;
    private Vector<String> ips;
    private JTextArea conList;
    private ArrayList<SampleServer> connections = new ArrayList<SampleServer>();

    public static void main(String[] args){
        new serverTest();
    }

    public serverTest()
    {
        super("Instant Messenger");
        userText = new JTextField(); //text field
        userText.addActionListener(
                new ActionListener(){
                    public void actionPerformed (ActionEvent event){
                        sendMessage(event.getActionCommand()); //sends the message
                        userText.setText("");
                    }
                }
        );
        add(userText, BorderLayout.SOUTH);
        users = new Vector();
        ips = new Vector();
        chatWindow = new JTextArea();
        conList = new JTextArea();
        conList.setEditable(false);
        add(new JScrollPane(chatWindow));
        add(new JScrollPane(conList), BorderLayout.EAST);
        conList.append("   ONLINE USERS    \n");
        setSize(300, 150);
        setDefaultCloseOperation(EXIT_ON_CLOSE);
        setVisible(true);

       try {
           server = new ServerSocket(6789, 100); //port number and only 100 can connect to the server
           while(true){
               try{
                    showMessage("Waiting for someone to connect...\n");
                    Socket connection = server.accept(); //once someone asked for connection, accepts this
                    //showMessage("Now connected to "+connection.getInetAddress().getHostName()); //converts the ip address to string

                    ips.add(connection.getInetAddress().getHostName()); // adds ip address of client to ips vector

                    BufferedReader fromC = new BufferedReader(new InputStreamReader(connection.getInputStream())); // gets what client sent through printwriter - username
                    String s = new String(fromC.readLine()); // saves as string
                    users.add(s); // saves username of client to users vector
                    String con = (connection.getInetAddress().getHostName());
                    showMessage(s + " / " + con + " has connected.");

                    Iterator c = users.iterator(); // username iterator
                    Iterator b = ips.iterator(); // ip address iterator

                    conList.setText("");

                    while(c.hasNext()) {

                        String d = (c.next()).toString(); // gets next element in users vector
                        String e = (b.next().toString()); // gets next element in ips vector
                        conList.append(d + "\n"); // displays username in online users list
                        conList.append("(" + e + ")\n\n"); // displays ip in online users list
                    }
                    final SampleServer se = new SampleServer(connection, s, con, this);
                    Thread t = new Thread(new Runnable(){
                        public void run()
                        {
                            se.run();
                        }
                    });
                    connections.add(se);
               }catch(EOFException eofException){
                   showMessage("\n Server ended the connection!");
               }
           }

       }catch(IOException ioException){
           ioException.printStackTrace();
       }
    }

    public void closeAll()
    {
        while (!connections.isEmpty())
        {
            connections.get(0).closeAll();
            connections.remove(0);
        }
    }

    public void sendMessage(String text)
    {
                showMessage("\n SERVER - " + text);
        for (SampleServer s : connections)
        {
            s.sendMessage(text);
        }
    }

    public void showMessage(final String text)
    {
       SwingUtilities.invokeLater( //updats GUI or threads
               new Runnable(){
                   public void run(){
                       chatWindow.append(text); //add string at the end of the chatWindow
                   }
               }
       );
    }
}