Java基础11——套接字(Socket)

1.网络基本概念

计算机网络就是指将地理位置不同的计算机通过通信线路连接起来,实现资源共享和信息传递。 网络编程就是通过程序实现两台(或多台)主机之间的数据通信。 要想实现这一目标,首先要建立连接,然后按照事先规定好的格式进行数据传输,从而完成主机之间的信息传输。

(1)IP地址和域名

IP地址是识别网络主机的唯一身份标识。 IP地址是由32位二进制数组成(IPv4为例),通常写成4个0~255之间的数字。 域名可看做是IP地址的别称,用字符进行描述,便于理解和记忆。 在网络通信过程中只能使用IP地址。 DNS是地址解析系统,实现域名与IP地址的自动转换工作。

(2)端口和Socket

端口是用于识别主机进程的标识。 Socket是主机IP地址+端口号。 网络编程也称为基于Socket的编程。

(3)C/S模式

Client是发起请求的一方,被称作客户端;Server是接受请求的另一方,被称作服务器端。 C/S模式称为客服端/服务器端模式,简称C/S模式。 B/S模式:特殊的C/S模式。 Browser是浏览器,不需要安装额外的客户端程序就能访问服务器端。

2.TCP和UDP协议

(1)TCP(Transmission Control Protocol——传输控制协议)是一种面向连接的可靠的传输协议。采用通信双方相互应答的方式来保证数据传送的可靠性。网络的通信开销增加,协议也更为复杂。大部分网络通信都采用TCP协议。

(2)UDP(User Datagram Protocol——用户数据报协议)是一种面向无连接的传输协议。不需要通信双方事先建立连接和应答就进行传输。协议简单,效率更高,但不保证通信的可靠性。适用一些简单的网络应用。

3.套接字

网络程序中的套接字用于将应用程序与端口连接起来。套接字是一个假想的连接装置,就像插插头的设备“插座”,用于连接电气与电线。Java将套接字抽象为类,创建Socket类对象就可以使用套接字了。

(1)概述

套接字,即socket,由IP地址+端口构成。 计算机网络中规定端口号由16位二进制数表示,即十进制数范围为0~65535。 0~1023端口为公认端口或熟知端口,被系统进程或常用服务所占用。选择端口时要选择1024以后的端口。 套接字根据连接端的不同可分为客户端套接字和服务器端套接字。 java.net.Socket类和java.net.ServerSocket类用于客户机与服务器端的网络编程。

(2)客户端套接字

客户端是发起连接请求的程序。 首先建立网络连接,在建立连接时需要指出服务器端的IP地址和端口号。 连接建立成功,就可以实现数据交互。数据交互时按照请求-响应模型由客户端向服务器端发送请求,服务器端根据请求内容进行处理,并将响应结果返回给客户端。 数据的交互过程可以进行多次,每次均按照请求-响应模型进行。 在数据交互结束后,关闭网络连接,释放占用的端口、内存等资源,结束客户端程序。

java.net.Socket类代表客户端连接。最常用的构造方法有两个:

public Socket(String host,int port)throws UnknownHostException, IOException
public Socket(InetAddress address,int port) throws IOException

交互操作是通过输入流/输出流完成的。获取输出流的方法:

public OutputStream getOutputStream() throws IOException

获取输入流的方法:

public InputStream getInputStream() throws IOException

(3)服务器端套接字

服务器端程序监听固定的端口。 当服务器端监听到客户端的连接请求后,与客户端建立一个网络连接。 连接建立成功后,双方进行数据交互。 数据交互结束,关闭服务器端,释放占用的资源。 在实际编程中,为解决多用户响应问题,通常采用多线程机制。

服务器端使用java.net.ServerSocket类的对象来表示服务器套接字。ServerSocket类的常用构造方法:

public ServerSocket(int port) throws IOException

port为连接指定的端口,如果为0,表示使用任何空闲的端口。在建立连接时,会创建一个连接请求队列,表示可以连接的最大请求数,默认为50。如果队列满时再收到连接请求,则拒绝该连接。另一个构造方法可以指定请求队列的长度:

public ServerSocket(int port,int backlog) throws IOException

参数backlog为大于0的正整数,表示队列的最大长度。如果该值小于等于0,则使用默认值。

创建好服务器套接字后,就可以进行连接监听了。连接监听的方法为:

public Socket accept() throws IOException 

此方法监听并接受到此套接字的连接。其在连接传入之前一直阻塞。 例如:

Socket socket=server_socket.accept(); 

一旦监听到请求并建立了socket连接后,就可以进行数据交互了。

例1:实现文件传输功能

客户端:

import java.io.*;
import java.net.Socket;

public class MyClient {
    public static void main(String[] args) {
        Socket client=null;
        DataInputStream dis=null;
        DataOutputStream dos=null;
        try {
            client=new Socket("127.0.0.1",9527);
            dis=new DataInputStream(client.getInputStream());
            String filename=dis.readUTF();
            File file=new File("d://"+filename+".txt");

            dos=new DataOutputStream(new FileOutputStream(file));
            int n=-1;
            byte[] buffer=new byte[1024];
            while( (n=dis.read(buffer))!=-1){
                dos.write(buffer,0,n);
            }


        }catch(Exception e){
            e.printStackTrace();
        }
        finally{
            try {
                dis.close();
                dos.flush();
                dos.close();
                client.close();
            } catch (IOException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        }
    }
}

服务器:

import java.io.*;
import java.net.ServerSocket;
import java.net.Socket;

public class MyServer {
    public static void main(String[] args) {

        Socket client=null;
        ServerSocket server= null;
        DataInputStream dis=null;
        DataOutputStream dos=null;
        try{
            server=new ServerSocket(9527);
            File file=new File("c://1.txt");
            dis=new DataInputStream(new FileInputStream(file));
            client=server.accept();
            dos=new DataOutputStream(client.getOutputStream());
            dos.writeUTF("你好");
            dos.flush();
            byte[] buffer=new byte[1024];
            int n=-1;
            while( (n=dis.read(buffer))!=-1 ){
                dos.write(buffer,0,n);
            }


        }catch(Exception e){
            e.printStackTrace();
        }finally{
            try {
                dos.flush();
                dos.close();
                dis.close();
                client.close();
                server.close();
            } catch (IOException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }

        }


    }
}

例2:实现聊天功能

客户端:

import java.io.IOException;
import java.io.PrintWriter;
import java.net.Socket;
import java.util.Scanner;

public class MyClient {

    public static void main(String[] args) throws IOException {
        Socket client=new Socket("127.0.0.1",9527);
        PrintWriter out=new PrintWriter(client.getOutputStream(),true);
        Scanner scanner=new Scanner(System.in);
        while(scanner.hasNext()){
            String line=scanner.nextLine();
            out.println(line);
        }
        scanner.close();
        out.close();
        client.close();


    }
}

服务器:

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.ServerSocket;
import java.net.Socket;

public class MyServer {
    public static void main(String[] args) throws IOException {
        ServerSocket server=new ServerSocket(9527);
        Socket client=server.accept();
//  字节流转换为字符流
        BufferedReader r=new BufferedReader(new InputStreamReader(client.getInputStream()));

        boolean flag=true;
        while(flag){
            String line=r.readLine().trim();
            if(line.equals("exit")){
                flag=false;
            }else{
                System.out.println(line);
            }
        }
        r.close();
        client.close();
        server.close();


    }
}

 

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值