
客户端:
package chatroom;
import javaawt;
import javaawtevent;
import javanet;
import javaio;
import javaxswing;
public class client extends JFrame implements ActionListener,Runnable{
JPanel conn,text,send;
JLabel name,sendto;
JComboBox list;
JButton con,snd,clear;
JTextArea talk;
JTextField who,say;
JScrollPane jsp;
Socket client;
InputStream is;
OutputStream os;
PrintStream ps;
BufferedReader br;
String receive,yousay;
Thread th;
DataInputStream dis;
Double tof;
client()
{
super("聊天室客户端");
thissetSize(800,600);
thissetResizable(false);
conn=new JPanel();
text=new JPanel();
send=new JPanel();
thisgetContentPane()add(conn);
connsetBounds(0, 0, thisgetWidth(),50);
name=new JLabel("姓名:");
who=new JTextField();
con=new JButton("连接");
connsetLayout(null);
connadd(name);
namesetBounds(30, 10, 50, 25);
connadd(who);
whosetBounds(80, 10, 150, 25);
connadd(con);
consetBounds(250,10, 60, 25);
thisgetContentPane()add(text);
textsetBounds(0,50,thisgetWidth(),450);
textsetLayout(new BorderLayout());
jsp=new JScrollPane();
talk=new JTextArea();
jspgetViewport()setView(talk);
textadd(jsp,"Center");
talksetLineWrap(true);
thisgetContentPane()add(send);
sendsetLayout(null);
sendsetBounds(0, 480, thisgetWidth(), 150);
sendto=new JLabel("发送到:");
snd=new JButton("发送");
list=new JComboBox();
say=new JTextField();
clear=new JButton("清空");
sendadd(sendto);
sendtosetBounds(30, 525, 50, 25);
sendadd(list);
listsetBounds(100, 525, 75, 25);
sendadd(say);
saysetEditable(true);
saysetBounds(200, 525, 300, 25);
sendadd(snd);
sndsetBounds(520, 525, 100, 25);
sendadd(clear);
clearsetBounds(650, 525, 100, 25);
thissetDefaultCloseOperation(JFrameEXIT_ON_CLOSE);
thissetVisible(true);
conaddActionListener(this);
sndaddActionListener(this);
}
public void actionPerformed(ActionEvent ae) {
if (aegetActionCommand()equals("连接"))
{
try
{
client=new Socket(InetAddressgetLocalHost(),55555);
talkappend("连接成功\n");
consetText("断开");
is=clientgetInputStream();
os=clientgetOutputStream();
th=new Thread(this);
String id=whogetText();
byte b[]=idgetBytes();
DataOutputStream dos=new DataOutputStream(os);
int len=blength;
doswriteInt(len);
doswrite(b);
thstart();
}catch(Exception e){talkappend("连接失败\n"+etoString()+"0000");}
}
else if(aegetSource()==snd)
{
if(listgetSelectedItem()toString()=="所有人")
{
yousay="@open"+saygetText();
byte b[]=yousaygetBytes();
DataOutputStream dos=new DataOutputStream(os);
try{
int len=blength;
doswriteInt(len);
doswrite(b);
}catch(Exception e)
{
Systemoutprint(etoString()+"1111");
}
}
else
{
yousay="@whisper"+saygetText();
byte b[]=yousaygetBytes();
byte w[]=listgetSelectedItem()toString()getBytes();
DataOutputStream dos=new DataOutputStream(os);
try{
int len=blength;
int wlen=wlength;
doswriteInt(len); //内容
doswrite(b);
doswriteInt(wlen); //发送对象
doswrite(w);
}catch(Exception e)
{
Systemoutprint(etoString()+"AAAA");
}
}
}
else if(aegetActionCommand()equals("断开"))
{
try
{
clientclose();
talkappend("连接已断开\n");
consetText("连接");
}catch(Exception e){Systemoutprintln(etoString()+"2222");}
}
}
public void run()
{
while(true)
{
try
{
dis=new DataInputStream(is);
tof=disreadDouble();
if(tof==11)
{
dis=new DataInputStream(is);
int number;
listremoveAllItems();
listaddItem("所有人");
number=disreadInt();
for(int i=0;i<number;i++)
{
int len=disreadInt();
byte b[]=new byte[len];
disread(b);
String name=new String(b);
listaddItem(name);
}
}
else if(tof==22)
{
try
{
dis=new DataInputStream(is);
int len=disreadInt();
byte b[]=new byte[len];
disread(b);
receive=new String(b);
talkappend(receive+"\n");
}catch(Exception e){JOptionPaneshowMessageDialog(this, "连接已断开","消息",JOptionPaneINFORMATION_MESSAGE);break;}
}
}catch(Exception e){JOptionPaneshowMessageDialog(this, "连接已断开","消息",JOptionPaneINFORMATION_MESSAGE);break;}
}
}
public static void main(String[] args) {
client cl=new client();
}
}
服务端:
package chatroom;
import javaawt;
import javaxswing;
import javanet;
import javautilVector;
import javaio;
public class server extends JFrame implements Runnable{
JPanel jp1;
JTextArea jta;
JScrollPane jsp;
Socket socket=null;
ServerSocket server;
InputStream is;
OutputStream os;
static int i=0,login;
int no;
static String s="";
Thread sr;
Thread th[]=new Thread[20];
static Vector ol=new Vector();
static public byte w[]=null;
static String from=""; //人名
static String to="";
static String fromtext=""; //内容
static String totext="";
server()
{
super("聊天室服务端");
thisgetContentPane()setLayout(new GridLayout(1,1));
thissetSize(400,300);
jp1=new JPanel();
jta=new JTextArea();
jsp=new JScrollPane();
thisgetContentPane()add(jp1);
jp1setLayout(new GridLayout(1,1));
jspgetViewport()setView(jta);
jp1add(jsp);
thissetDefaultCloseOperation(JFrameEXIT_ON_CLOSE);
setVisible(true);
}
public static void main(String[] args) {
server sr=new server();
srsr=new Thread(sr);
srsrstart();
sendtoall sta=new sendtoall();
returnfrom rf=new returnfrom(sr);
returnto rt=new returnto(sr);
stastart();
rfstart();
rtstart();
}
public void run()
{
try
{
server=new ServerSocket(55555);
while(true)
{
socket=serveraccept();
is=socketgetInputStream();
DataInputStream dis=new DataInputStream(is);
int len=disreadInt();
byte b[]=new byte[len];
disread(b);
String id=new String(b);
record v=new record(id,socket);
oladdElement(v);
for (int i=0;i<olsize();i++)
{
if (olelementAt(i)equals(v))
{
no=i;
}
}
login=1;
s=id+"已来到聊天室!";
th[no]=new Thread(new receive(this,no));
th[no]start();
}
}catch(Exception e){Systemoutprintln(etoString()+"aaaa");}
}
}
class receive implements Runnable
{
InputStream is;
OutputStream os;
server sr;
Socket sk;
int i;
String name;
String ip;
receive(server sr,int i)
{
thissr=sr;
thisi=i;
sk=((record)srolelementAt(i))ip;
name=((record)srolelementAt(i))name;
ip=((record)srolelementAt(i))ipgetInetAddress()toString();
}
public void run()
{
while(true)
{
try
{
is=skgetInputStream();
DataInputStream dis=new DataInputStream(is);
int len=disreadInt();
byte b[]=new byte[len];
disread(b);
String abc=new String(b);
srjtaappend(abc);
if(abcsubstring(0,5)equals("@open"))
{
servers=name+"["+ipsubstring(1, iplength())+"]"+"说:"+abcsubstring(5,abclength());
srjtaappend(servers+"\n");
}
else if(abcsubstring(0,8)equals("@whisper"))
{
int wlen=disreadInt();
srw=new byte[wlen];
disread(srw);
serverto=new String(srw);
serverfrom=((record)srolelementAt(i))name;
String ip=((record)srolelementAt(i))ipgetInetAddress()toString();
// servers=serverfrom+"对"+serverto+"["+ipsubstring(1, iplength())+"]"+"悄悄地说:"+abcsubstring(8,abclength());
serverfromtext="你对"+serverto+"["+ipsubstring(1, iplength())+"]"+"悄悄地说:"+abcsubstring(8,abclength());
servertotext=serverfrom+"["+ipsubstring(1, iplength())+"]"+"对你悄悄地说:"+abcsubstring(8,abclength());
srjtaappend(servers+"\n");
}
}catch(Exception e)
{
try
{
DataOutputStream dos=new DataOutputStream(os);
serverolremoveElementAt(i);
servers=name+"已离开聊天室";
serverlogin=1;
break;
}catch(Exception f){}
}
}
}
}
class sendtoall extends Thread
{
int len,number;
byte b[];
server sr;
Socket st;
OutputStream os;
DataOutputStream dos;
public void run()
{
while(true)
{
try
{
if(serverlogin==1)
{
number=0;
number=serverolsize();
dos=new DataOutputStream(os);
for(int i=0;i<serverolsize();i++)
{
st=((record)srolelementAt(i))ip;
os=stgetOutputStream();
dos=new DataOutputStream(os);
doswriteDouble(11);
doswriteInt(number);
for (int j=0;j<number;j++)
{
String name=((record)srolelementAt(j))name;
byte b[]=namegetBytes();
int len=blength;
doswriteInt(len);
doswrite(b);
}
}
serverlogin=0;
}
else if(!serversequals("")&&srolsize()>0)
{
b=serversgetBytes(); //String类型中 汉字占一个字节,但是byte类型中,汉字占两个字节
len=blength;
//len=serverslength();
//b=new byte[len];
//b=serversgetBytes();
for(int i=0;i<serverolsize();i++)
{
st=((record)srolelementAt(i))ip;
os=stgetOutputStream();
DataOutputStream dos=new DataOutputStream(os);
doswriteDouble(22);
doswriteInt(len);
doswrite(b);
}
servers="";
}
}catch(Exception e){Systemoutprintln(etoString()+"sdasd");}
}
}
}
class returnfrom extends Thread
{
int len,wlen;
byte b[];
byte w[];
server sr;
Socket st;
OutputStream os;
DataOutputStream dos;
//String from="",to="";
returnfrom(server sr)
{
thissr=sr;
}
public void run()
{
while(true)
{
if(!serverfromtextequals(""))
{
b=serverfromtextgetBytes();
len=blength;
srjtaappend(srfromtext);
try
{
for(int i=0;i<serverolsize();i++)
{
if(((record)srolelementAt(i))nameequals(serverfrom))
{
st=((record)srolelementAt(i))ip;
os=stgetOutputStream();
DataOutputStream dos=new DataOutputStream(os);
doswriteDouble(22);
doswriteInt(len);
doswrite(b);
}
}
}catch(Exception e){Systemoutprintln(etoString()+">
Java可以使用Socket编程实现聊天功能。Socket是一种网络通信协议,它可以在不同的主机之间传输数据。在聊天功能中,一般有客户端和服务器两个角色。
客户端是发送消息的一方,它需要创建一个Socket对象,指定要连接的服务器的IP地址和端口号。然后,客户端通过Socket对象的输入输出流向服务器发送和接收消息。在接收消息时,客户端需要启动一个线程不断监听服务器的消息,并将接收到的消息展示给用户。
服务器端则是接收和转发消息的一方。服务器需要创建一个ServerSocket对象,指定监听的端口号。当有客户端连接到服务器时,服务器通过Socket对象的输入输出流向客户端发送和接收消息。在接收到客户端的消息后,服务器需要将消息转发给其他客户端,以实现聊天室的功能。
需要注意的是,在聊天功能中,数据的传输是通过网络进行的,因此需要考虑数据传输的稳定性和安全性。例如,可以使用加密算法对聊天数据进行加密,确保聊天数据的安全性。此外,在多用户同时连接的情况下,还需要考虑服务器的并发处理能力。
package API_Day09;
import javaioBufferedReader;
import javaioIOException;
import javaioInputStream;
import javaioInputStreamReader;
import javaioOutputStream;
import javaioOutputStreamWriter;
import javaioPrintWriter;
import javanetSocket;
import javautilScanner;
/
控制台聊天程序
客户端应用程序
@author Jacob
/
public class chatClient
{
//客户端用于与服务端连接的Socket
private Socket clientSocket;
/
构造方法,客户端初始化
/
public chatClient()
{
try
{
/
socket(String host, int port)
地址: IP地址,用来定位网络上的计算机
端口: 用来找到远端计算机上用来连接的服务端应用程序
/
clientSocket = new Socket("localhost",12580);
}
catch (Exception e)
{
eprintStackTrace();
}
}
/
客户端昵称验证方法
@param 为Scanner
/
private void inputNickName(Scanner scan) throws Exception
{
String nickName = null;
//创建输出流
PrintWriter pw = new PrintWriter(
new OutputStreamWriter(clientSocketgetOutputStream(),
"UTF-8"),true);
//创建输入流
BufferedReader br = new BufferedReader(
new InputStreamReader(
clientSocketgetInputStream(),"UTF-8"));
while(true)
{
Systemoutprintln("请创建您的昵称:");
nickName = scannextLine();
if (nickNametrim()equals(""))
{
Systemoutprintln("昵称不得为空");
}
else
{
pwprintln(nickName);
String pass = brreadLine();
if(pass!=null&&!passequals("OK"))
{
Systemoutprintln("昵称已经被占用,请更换!");
}
else
{
Systemoutprintln("你好!"+nickName+"可以开始聊天了");
break;
}
}
}
}
/
客户端启动的方法
/
public void start()
{
try
{
/
创建Scanner,读取用户输入内容
目的是设置客户端的昵称
/
Scanner scanner = new Scanner(Systemin);
inputNickName(scanner);
/
将用于接收服务器端发送过来的信息的线程启动
/
Runnable run = new GetServerMsgHandler();
Thread t = new Thread(run);
tstart();
/
建立输出流,给服务端发信息
/
OutputStream os = clientSocketgetOutputStream();
OutputStreamWriter osw = new OutputStreamWriter(os,"UTF-8");
PrintWriter pw = new PrintWriter(osw,true);
while(true)
{
pwprintln(scannernextLine());
}
}
catch(Exception e)
{
eprintStackTrace();
}
finally
{
if(clientSocket !=null)
{
try
{
clientSocketclose();
}
catch(IOException e)
{
eprintStackTrace();
}
}
}
}
/
该线程体用来循环读取服务端发送过来的信息
并输出到客户端的控制台
@param args
/
class GetServerMsgHandler implements Runnable
{
@Override
public void run()
{
try
{
InputStream is = clientSocketgetInputStream();
InputStreamReader isr = new InputStreamReader(is,"UTF-8");
BufferedReader br = new BufferedReader(isr);
String msgString = null;
while((msgString = brreadLine())!= null)
{
Systemoutprintln("服务端提示:"+ msgString);
}
}
catch(Exception e)
{
eprintStackTrace();
}
}
}
public static void main(String[] args)
{
chatClient client = new chatClient();
clientstart();
}
}
package API_Day09;
import javaioBufferedReader;
import javaioIOException;
import javaioInputStream;
import javaioInputStreamReader;
import javaioOutputStream;
import javaioOutputStreamWriter;
import javaioPrintWriter;
import javanetServerSocket;
import javanetSocket;
import javautilHashMap;
import javautilMap;
import javautilconcurrentExecutorService;
import javautilconcurrentExecutors;
/
控制台聊天程序
服务端应用程序
@author Jacob
/
public class chatServer
{
/
ServerSocket 是运行在服务端的Socket
用来监听端口,等待客户端的连接,
一旦连接成功就会返回与该客户端通信的Socket
/
private ServerSocket serverSocket;
/
创建线程池来管理客户端的连接线程
避免系统资源过度浪费
/
private ExecutorService threadPool;
/
该属性用来存放客户端之间私聊的信息
/
private Map<String,PrintWriter> allOut;
/
构造方法,服务端初始化
/
public chatServer()
{
try
{
/
创建ServerSocket,并申请服务端口
将来客户端就是通过该端口连接服务端程序的
/
serverSocket = new ServerSocket(12580);
/
初始化Map集合,存放客户端信息
/
allOut = new HashMap<String, PrintWriter>();
/
初始化线程池,设置线程的数量
/
threadPool = ExecutorsnewFixedThreadPool(10);
/
初始化用来存放客户端输出流的集合,
每当一个客户端连接,就会将该客户端的输出流存入该集合;
每当一个客户端断开连接,就会将集合中该客户端的输出流删除;
每当转发一条信息,就要遍历集合中的所有输出流(元素)
因此转发的频率高于客户端登入登出的频率,
还是应该使用ArrayList来存储元素,仅限群聊,私聊不行
allOut = new ArrayList<PrintWriter>();
/
}
catch (Exception e)
{
eprintStackTrace();
}
}
/
将客户端的信息以Map形式存入集合中
/
private void addOut(String key,PrintWriter value)
{
synchronized(this)
{
allOutput(key, value);
}
}
/
将给定的输出流从共享集合中删除
参数为客户端nickName,作为Map的key键
/
private synchronized void removeOut(String key)
{
allOutremove(key);
Systemoutprintln("当前在线人数为:"+ allOutsize());
}
/
将给定的消息转发给所有客户端
/
private synchronized void sendMsgToAll(String message)
{
for(PrintWriter out: allOutvalues())
{
outprintln(message);
Systemoutprintln("当前在线人数为:"+ allOutsize());
}
}
/
将给定的消息转发给私聊的客户端
/
private synchronized void sendMsgToPrivate(String nickname,String message)
{
PrintWriter pw = allOutget(nickname); //将对应客户端的聊天信息取出作为私聊内容发送出去
if(pw!=null)
{
pwprintln(message);
Systemoutprintln("当前在线私聊人数为:"+ allOutsize());
}
}
/
服务端启动的方法
/
public void start()
{
try
{
while(true)
{
/
监听10086端口
/
Systemoutprintln("等待客户端连接 ");
/
Socket accept() 这是一个阻塞方法,会一直在10086端口进行监听
直到一个客户端连接上,此时该方法会将与这个客户端进行通信的Socket返回
/
Socket socket = serverSocketaccept();
Systemoutprintln("客户端连接成功! ");
/
启动一个线程,由线程来处理客户端的请求,这样可以再次监听
下一个客户端的连接了
/
Runnable run = new GetClientMsgHandler(socket);
threadPoolexecute(run); //通过线程池来分配线程
}
}
catch(Exception e)
{
eprintStackTrace();
}
}
/
该线程体用来处理给定的某一个客户端的消息,循环接收客户端发送
的每一个字符串,并输出到控制台
@author Jacob
/
class GetClientMsgHandler implements Runnable
{
/
该属性是当前线程处理的具体的客户端的Socket
@see javalangRunnable#run()
/
private Socket socket;
/
获取客户端的地址信息
private String hostIP;
/
/
获取客户端的昵称
/
private String nickName;
/
创建构造方法
/
public GetClientMsgHandler(Socket socket)
{
thissocket = socket;
/
获取远端客户的Ip地址信息
保存客户端的IP地址字符串
InetAddress address = socketgetInetAddress();
hostIP = addressgetHostAddress();
/
}
/
创建内部类来获取昵称
/
private String getNickName() throws Exception
{
try
{
//服务端的输入流读取客户端发送来的昵称输出流
InputStream iin = socketgetInputStream();
InputStreamReader isr =
new InputStreamReader(iin,"UTF-8");
BufferedReader bReader = new BufferedReader(isr);
//服务端将昵称验证结果通过自身的输出流发送给客户端
OutputStream out = socketgetOutputStream();
OutputStreamWriter iosw =
new OutputStreamWriter(out,"UTF-8");
PrintWriter ipw = new PrintWriter(iosw,true);
//读取客户端发来的昵称
String nameString = bReaderreadLine();
while(true)
{
if(nameStringtrim()length()==0)
{
ipwprintln("FAIL");
}
if(allOutcontainsKey(nameString))
{
ipwprintln("FAIL");
}
else
{
ipwprintln("OK");
return nameString;
}
nameString = bReaderreadLine();
}
}
catch(Exception e)
{
throw e;
}
}
@Override
public void run()
{
PrintWriter pw = null;
try
{
/
通过客户端的Socket获取客户端的输出流
用来将消息发送给客户端
/
OutputStream os = socketgetOutputStream();
OutputStreamWriter osw = new OutputStreamWriter(os,"UTF-8");
pw = new PrintWriter(osw,true);
/
将客户昵称和其所说的话作为元素存入共享集合HashMap中
/
nickName = getNickName();
addOut(nickName, pw);
Threadsleep(100);
/
服务端通知所有客户端,某用户登录
/
sendMsgToAll("[系统通知]:欢迎"+nickName+"登陆聊天室!");
/
通过客户端的Socket获取输入流
读取客户端发送来的信息
/
InputStream is = socketgetInputStream();
InputStreamReader isr = new InputStreamReader(is,"UTF-8");
BufferedReader br = new BufferedReader(isr);
String msgString = null;
while((msgString = brreadLine())!=null)
{
//验证是否是私聊
if(msgStringstartsWith("@"))
{
/
私聊格式:@昵称:内容
/
int index = msgStringindexOf(":");
if(index >=0)
{
//获取昵称
String name = msgStringsubstring(1,index);
String info = msgStringsubstring(index+1,msgStringlength());
info = nickName + "对你说:"+ info;
//将私聊信息发送出去
sendMsgToPrivate(name, info);
//服务端不在广播私聊的信息
continue;
}
}
/
遍历所有输出流,将该客户端发送的信息转发给所有客户端
/
Systemoutprintln(nickName+"说:"+ msgString);
sendMsgToAll(nickName+"说:"+ msgString);
}
}
catch (Exception e)
{
/
因为Win系统用户的客户端断开连接后,brreadLine()方法读取
不到信息就会抛出异常,而Linux系统会持续发送null;
因此这里就不在将捕获的异常抛出了。
/
}
finally
{
/
当执行到此处时,说明客户端已经与服务端断开连接
则将该客户端存在共享集合中的输出流删除
/
removeOut(nickName);
/
通知所有客户端,某某客户已经下线
/
sendMsgToAll("[系统通知]:"+nickName + "已经下线了。");
/
关闭socket,则通过Socket获取的输入输出流也一同关闭了
/
if(socket!=null)
{
try
{
socketclose();
}
catch(IOException e)
{
eprintStackTrace();
}
}
}
}
}
public static void main(String[] args)
{
chatServer server = new chatServer();
serverstart();
}
}
我的作业,供你参考
以上就是关于急需一个用java 语言写的聊天程序全部的内容,包括:急需一个用java 语言写的聊天程序、用JAVA 编写简单网络聊天程序、java是如何实现聊天功能的等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!
欢迎分享,转载请注明来源:内存溢出
微信扫一扫
支付宝扫一扫
评论列表(0条)