通信是网络编程中重要的组成部分,而socket编程是网络编程的基础。利用socket可以实现客户端和服务器端的通信。下面我先把客户端和服务器端的代码粘上去再进行详细的分析。

package test1;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.ServerSocket;
import java.net.Socket;
import org.junit.Test;

public class test2 {
@Test
public void client(){
	Socket socket = null;
	OutputStream oo = null;
	FileInputStream fis = null;
	InputStream io = null;
	try {
	    //1.建立socket对象实例
		socket = new Socket("127.0.0.1", 8989);
		//2.调用getOutputStream()方法,目的是建立数据缓冲区,将数据发送到服务器端
		oo = socket.getOutputStream();
		//3.创建FileInputStream对象实例,将要发送的文件写入到输出流数据缓冲区中
		File file=new File("D:\\123.avi");
		fis = new FileInputStream(file);
		byte[] b=new byte[1024];
		int len;
		while((len=fis.read(b))!=-1){
			oo.write(b, 0, len);
		}
		//这行代码的意思是告诉服务器端我发送的数据完毕。
		socket.shutdownOutput();
		//4.调用getInputStream()方法:目的是接收从服务器端发送的数据
		io = socket.getInputStream();
		byte[] b1=new byte[1024];
		int len1;
		while((len1=io.read(b1))!=-1){
			String str=new String(b1, 0, len1);
			System.out.println(str);
		}
	}  catch (Exception e) {
		// 关闭各个连接
		e.printStackTrace();
	}finally{
		if(io != null){
			try {
				io.close();
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
		if(fis !=null){
			try {
				fis.close();
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
		if(oo != null){
			try {
				oo.close();
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
		if(socket !=null){
			try {
				socket.close();
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
	}
}
@Test
public void server(){
	ServerSocket ss = null;
	Socket s = null;
	InputStream is = null;
	FileOutputStream fos = null;
	OutputStream os = null;
	try {
	   //1.创建ServerSocket对象的实例。
		ss = new ServerSocket(8989);
		//2.调用accept()方法来创建通信连接,期间经历了三次握手,只不过我们看不到
		s = ss.accept();
		//3.调用getInputStream()方法来接收客户端发送的文件
		is = s.getInputStream();
		//4.创建FileOutputStream()对象实例来保存从客户端发送的文件,并将文件写入到对象中
		fos = new FileOutputStream(new File("D:\\123567.avi"));
		byte[] b=new byte[1024];
		int len;
		while((len=is.read(b))!=-1){
			fos.write(b, 0, len);
		}
		//5.向客户端反馈信息,将信息储存在数据缓冲区中
		os = s.getOutputStream();
		os.write("你发送的视频我已经接收".getBytes());
	}  catch (Exception e) {
		// TODO Auto-generated catch block
		e.printStackTrace();
	}finally{
		if(os !=null){
			try {
				os.close();
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
		if(fos != null){
			try {
				fos.close();
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}	
		}
		if(is !=null){
			try {
				is.close();
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}	
		}
		if(s != null){
			try {
				s.close();
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
		if(ss != null){
			try {
				ss.close();
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
	}
}
}

基本知识点补充:
上述代码块中我利用了junit进行模块测试,利用junit进行测试需要导入junit-4.12.jar和hamcrest-core-1.3.jar这两个jar包。在上面的代码中用到的知识点有socket,输入流(InputStream)和输出流(OutputStream)以及文件输入流(FileInputStream)和文件输出流(FileOutputStream)。
1.
从客户端(Client)来看:socket.getInputStream()方法是接收服务端发送的数据。socket.getOutputStream()方法是类似于一个数据缓冲器,用于存储向服务器端发送的数据。
从服务器端(Server)来看: socket.getInputStream()方法是接收客户端发送的数据。socket.getOutputStream()方法是类似于一个数据缓冲器,用于存储向客户端发送的数据。
2.
FileInputStream:文件输入流是用来读入数据的 ----------->读入
FileOutputStream:文件输出流是用来写出数据的----------->写出
3.计算机网络中三次握手实现原理
在TCP/IP协议中,TCP协议提供可靠的连接服务,采用三次握手建立一个连接。
第一次握手:建立连接时,客户端发送syn包(syn=j)到服务器,并进入SYN_SEND状态,等待服务器确认;
第二次握手:服务器收到syn包,必须确认客户的SYN(ack=j+1),同时自己也发送一个SYN包(syn=k),即SYN+ACK包,此时服务器进入SYN_RECV状态; 第三次握手:客户端收到服务器的SYN+ACK包,向服务器发送确认包ACK(ack=k+1),此包发送完毕,客户端和服务器进入ESTABLISHED状态,完成三次握手。 完成三次握手,客户端与服务器开始传送数据.

如果大家有什么疑问的可以提出问题我来一一为大家解答。