java客户端_Java 客户端服务器范例

本文介绍了Java中客户端服务器模型的实现,包括客户端的Socket连接和数据发送,以及服务器端的单线程和多线程处理。在服务器端,从单线程版本逐步演进到多线程版本,最后引入了线程池来优化资源管理。通过创建ServerSocket监听端口,接收客户端连接,并使用ExecutorService实现线程池处理多个并发请求。
摘要由CSDN通过智能技术生成

最近在面试,虽然学习了一些新的框架,但是可能问类似于客户端服务器模型,然后根据其设计,所以就根据面试内容梳理一下客户端服务器模型。

客户端基本思路:

1.创建Socket实例,设置端口和IP地址等

2.通过Socket实例,获取到流对象

3.通过流对象,向其中输入数据 ,并且在完成后实现关闭流。

(注意事情:1.需要进行异常处理 2.注意关闭流和Socket 3.低级流和高级流的关闭顺序)

//客户端程序

package ServerSocket;

import java.io.BufferedOutputStream;

import java.io.IOException;

import java.io.OutputStream;

import java.net.Socket;

public class ClientDome {

public static void main(String[] args) {

Socket socket =null;

OutputStream outputStream=null;

BufferedOutputStream bufferedOutputStream=null;

try {

socket=new Socket("localhost", 6060);

outputStream=socket.getOutputStream();

bufferedOutputStream =new BufferedOutputStream(outputStream);

String str ="Client Dome ..... Are you ok";

bufferedOutputStream.write(str.getBytes());

bufferedOutputStream.flush();

} catch (Exception e) {

e.printStackTrace();

}finally{

try {

bufferedOutputStream.close();

outputStream.close();

socket.close();

} catch (IOException e) {

e.printStackTrace();

}

}

}

}

服务器模型构建:

1.创建一个ServerSocket对象,进行端口监听。

2.while(true)重复监听

3.通过端口监听对象 获取Socket实例 并且获取到网络流

4.输出网络流数据 并且关闭流

(注意事情:端口监听一次 获取监听对象多次 低级流和高级流的关闭顺序)

//首先这是单线程版本

package ServerSocket;

import java.io.BufferedInputStream;

import java.io.IOException;

import java.io.InputStream;

import java.net.ServerSocket;

import java.net.Socket;

public class ServerSocketDome {

@SuppressWarnings("null")

public static void main(String[] args) {

// 1.建立监听

ServerSocket serverSocket = null;

InputStream inputStream = null;

BufferedInputStream bufferedInputStream = null;

@SuppressWarnings("unused")

Socket socket = null;

try {

serverSocket =new ServerSocket(6060);

while(true){

socket = serverSocket.accept();

inputStream = socket.getInputStream();

bufferedInputStream = new BufferedInputStream(inputStream);

byte[] bytes=new byte[10];

int len=0;

while((len=bufferedInputStream.read(bytes))!=-1){

System.out.print(new String(bytes, 0, len));

}

}

} catch (IOException e) {

e.printStackTrace();

} finally {

try {

if(bufferedInputStream!=null){

bufferedInputStream.close();

inputStream.close();

socket.close();

}

} catch (IOException e) {

e.printStackTrace();

}

}

}

}

多线程版本怎么操作,这里即将引入多线程

服务器版本多线程主要是对于请求分线程操作 ,一次连接会单独分配线程

package ServerSocket;

import java.io.BufferedInputStream;

import java.io.IOException;

import java.io.InputStream;

import java.net.ServerSocket;

import java.net.Socket;

//为了应对面试需要 尝试根据自己思路写一个新的多线程版本试试

//其实多线程版本是根据单线程改进而来

//具体而言 多线程的服务器 是应对多条请求 不同线程进行处理

public class ServerSocketThreadDome {

public static void main(String[] args) {

//当然 主线程的端口监听是不能修改的

ServerSocket serverSocket = null;

//标准web服务器的端口是8080

int port=6060;

try {

serverSocket=new ServerSocket(port);

Socket socket=null;

while(true){

socket=serverSocket.accept();

new Thread(new Server(socket)).start();

}

} catch (IOException e) {

e.printStackTrace();

}finally{

if(serverSocket!=null){

try {

serverSocket.close();

} catch (IOException e) {

e.printStackTrace();

}

}

}

}

}

//这里的多线程说白了 就是为了应对多条请求而处理的结果

//也就是客户端对象

class Server implements Runnable{

private Socket socket;

public Server(Socket socket) {

super();

this.socket = socket;

}

@Override

public void run() {

InputStream inputStream=null;

BufferedInputStream bufferedInputStream =null;

try {

inputStream = socket.getInputStream();

bufferedInputStream=new BufferedInputStream(inputStream);

byte[] bytes=new byte[1024];

int len=0;

while((len=bufferedInputStream.read(bytes))!=-1){

System.out.print(new String(bytes, 0, len));

System.out.println("当前线程:"+Thread.currentThread().getName());

}

} catch (IOException e) {

// TODO Auto-generated catch block

e.printStackTrace();

}finally{

try {

if(bufferedInputStream!=null){

bufferedInputStream.close();

inputStream.close();

socket.close();

}

} catch (IOException e) {

e.printStackTrace();

}

}

}

}

那么我们引入线程池的概念 有时候面试可能会问线程池

packageServerSocket;importjava.io.BufferedInputStream;importjava.io.IOException;importjava.io.InputStream;importjava.net.ServerSocket;importjava.net.Socket;importjava.util.concurrent.ExecutorService;importjava.util.concurrent.Executors;//首先大话一下线程池,线程池类似于中介结果,我需要的时候找中介借一些人过来//不需要的时候中介自己回去 我不需要提供其他待遇等等//就是传说中的国企或者大型企业的外包部门

public classServerSocketPoolDome {public static voidmain(String[] args) {

ServerSocket serverSocket= null;//标准web服务器的端口是8080

int port=6060;try{

serverSocket=newServerSocket(port);

Socket socket=null;

ExecutorService executorService=Executors.newCachedThreadPool();while(true){

socket=serverSocket.accept();

executorService.execute(newServerPool(socket));

}

}catch(IOException e) {

e.printStackTrace();

}finally{if(serverSocket!=null){try{

serverSocket.close();

}catch(IOException e) {

e.printStackTrace();

}

}

}

}

}//这里的多线程说白了 就是为了应对多条请求而处理的结果//也就是客户端对象

class ServerPool implementsRunnable{privateSocket socket;publicServerPool(Socket socket){super();this.socket =socket;

}

@Overridepublic voidrun() {

InputStream inputStream=null;

BufferedInputStream bufferedInputStream=null;try{

inputStream=socket.getInputStream();

bufferedInputStream=newBufferedInputStream(inputStream);byte[] bytes=new byte[1024];int len=0;while((len=bufferedInputStream.read(bytes))!=-1){

System.out.print(new String(bytes, 0, len));

System.out.println("当前线程:"+Thread.currentThread().getName());

}

}catch(IOException e) {//TODO Auto-generated catch block

e.printStackTrace();

}finally{try{if(bufferedInputStream!=null){

bufferedInputStream.close();

inputStream.close();

socket.close();

}

}catch(IOException e) {

e.printStackTrace();

}

}

}

}

线程池的使用很爽,接下来看看线程池的源码

public static ExecutorService newCachedThreadPool() {

return new ThreadPoolExecutor(0, Integer.MAX_VALUE,

60L, TimeUnit.SECONDS,

new SynchronousQueue());

}

//线程池创建一个缓冲的线程池

//也就设置线程数目 和 活动时间 以及具体执行的方式

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值