zoukankan      html  css  js  c++  java
  • 网络编程

    1. 网络概念

    把多台计算机通过物理线路连接起来,就形成了网络。目的在于交换数据和共享信息。

     1)网络通信的三要素

    【1】IP地址:唯一标识网络上的每一台计算机。两台计算机之间通信的必备有素

    【2】端口号:计算机中应用的标号(代表一个应用程序)

     0-1024系统使用或保留端口

    常见端口:http:80 stmp: 25 ftp:21

    有效端口0-65536,开发者可以的端口是1025-65536之间。一些第三方引用如mysql:3306 oracle:1251。

    【3】通信协议:通信的规则TCP,UDP

    2) 网络通信模型

     

    IP地址分类

     

    特殊IP

    0.0.0.0:本机

    127.0.0.1:本机回环地址,用于本机测试

    255.255.255.255:当前子网,一般用于向当前子网广播信息

    2.  InetAddress

    InetAddress 表示IP地址。

     1 publicclass Test01 {
     2 
     3      publicstaticvoid main(String[] args) {
     4 
     5          // 获取本机IP地址
     6 
     7          InetAddress ip1;
     8 
     9          try {
    10 
    11               ip1 = InetAddress.getLocalHost();
    12 
    13               // USER-20180113BT/192.168.2.56
    14 
    15               System.out.println(ip1.toString());
    16 
    17              
    18 
    19               // 获取主机名称
    20 
    21               System.out.println(ip1.getHostName());
    22 
    23               System.out.println(ip1.getHostAddress());
    24 
    25              
    26 
    27          } catch (UnknownHostException e) {
    28 
    29               e.printStackTrace();
    30 
    31          }
    32 
    33      }
    34 
    35 }

    3.  TCP编程

    TCP编程中,如果要完成通信,通信双方必须要创建socket,通过socket完成通信。

    TCP通信步骤

    [1]服务器启动ServerSocket作为通信的Server端,等待客户端链入。

    [2]客户端创建Socket作为通信的Client端

    [3]Client端链入Server端后建立可靠的双向的持续性的点对点的通讯连接,即可通信。

    案例:完成一次单向通信。

    服务器端

     1 package cn.sxt01.net01;
     2 
     3  
     4 
     5 import java.io.IOException;
     6 
     7 import java.io.OutputStream;
     8 
     9 import java.net.ServerSocket;
    10 
    11 import java.net.Socket;
    12 
    13  
    14 
    15 publicclass Server01 {
    16 
    17      publicstaticvoid main(String[] args) {
    18 
    19         
    20 
    21          System.out.println("服务器启动...");
    22 
    23         
    24 
    25          // 【1】创建server socket
    26 
    27          ServerSocket serverSocket = null;
    28 
    29          Socket clientSocket = null;
    30 
    31          try {
    32 
    33         
    34 
    35               serverSocket = new ServerSocket(8000);
    36 
    37               // 【2】等待客户端的链入->阻塞式函数->监听8000端口,看是否有client链入
    38 
    39               clientSocket = serverSocket.accept();
    40 
    41              
    42 
    43               System.out.println(clientSocket.getInetAddress().getHostAddress()+"链入!");
    44 
    45         
    46 
    47               // 【3】给客户端主动发信息
    48 
    49               OutputStream out = clientSocket.getOutputStream();
    50 
    51              
    52 
    53               String msg = "hello 兄弟";
    54 
    55               byte[] buf = msg.getBytes("UTF-8");
    56 
    57               out.write(buf);
    58 
    59               clientSocket.shutdownOutput();
    60 
    61              
    62 
    63               out.close();
    64 
    65              
    66 
    67         
    68 
    69          } catch (IOException e) {
    70 
    71               e.printStackTrace();
    72 
    73          }
    74 
    75      }
    76 
    77 }

    客户端

     1 package cn.sxt02.net01;
     2 
     3  
     4 
     5 import java.io.IOException;
     6 
     7 import java.io.InputStream;
     8 
     9 import java.net.Socket;
    10 
    11  
    12 
    13 publicclass Client01 {
    14 
    15     publicstaticvoid main(String[] args) {
    16 
    17         System.out.println("客户端运行...");
    18 
    19        
    20 
    21         // 【1】创建客户端socket
    22 
    23         Socket socket = null;
    24 
    25         try {
    26 
    27             socket = new Socket("192.168.2.56", 8000);
    28 
    29            
    30 
    31             // 【2】接收来自服务器的消息
    32 
    33             InputStream in = socket.getInputStream();
    34 
    35             byte[] buf = newbyte[1024];
    36 
    37             intlen = in.read(buf);
    38 
    39            
    40 
    41             String msg = new String(buf, 0, len, "UTF-8");
    42 
    43             System.out.println(msg);
    44 
    45            
    46 
    47         } catch (IOException e) {
    48 
    49             e.printStackTrace();
    50 
    51         }
    52 
    53     }
    54 
    55 }

    常见问题

    [1]端口被占用

    java.net.BindException: Address already in use: JVM_Bind

         at java.net.DualStackPlainSocketImpl.bind0(Native Method)

         at java.net.DualStackPlainSocketImpl.socketBind(DualStackPlainSocketImpl.java:106)

         at java.net.AbstractPlainSocketImpl.bind(AbstractPlainSocketImpl.java:387)

         at java.net.PlainSocketImpl.bind(PlainSocketImpl.java:190)

         at java.net.ServerSocket.bind(ServerSocket.java:375)

         at java.net.ServerSocket.<init>(ServerSocket.java:237)

         at java.net.ServerSocket.<init>(ServerSocket.java:128)

         at cn.sxt01.net02.Server01.main(Server01.java:19)

    [2]服务器未启动

    java.net.ConnectException: Connection refused: connect

         at java.net.DualStackPlainSocketImpl.connect0(Native Method)

         at java.net.DualStackPlainSocketImpl.socketConnect(DualStackPlainSocketImpl.java:79)

         at cn.sxt02.net02.Client01.main(Client01.java:15)

    [3]连接超时异常SocketTimeoutException

    当网速很慢时,可能发生连接超时异常。

    需求:在控制台输入用户名和密码,如果输入正确提示登录成功,否则登录失败。

     服务器端

     1 public class Test01 {
     2     public static void main(String[]args) throws IOException, ClassNotFoundException{
     3         
     4         System.out.println("服务器启动中...");
     5         ServerSocket serverSocket=new ServerSocket(11000);
     6         while(true){
     7             Socket clinetSocket=serverSocket.accept();
     8             MyThread myThread=new MyThread(clinetSocket);
     9             myThread.start();
    10         }
    11     }
    12 }
     1 public class MyThread extends Thread {
     2 
     3     private Socket socket;
     4 
     5     public MyThread() {
     6         super();
     7     }
     8 
     9     public MyThread(Socket socket) {
    10         super();
    11         this.socket = socket;
    12     }
    13     @Override
    14     public void run() {
    15         InputStream in=null;
    16         ObjectInputStream ois=null;
    17         OutputStream out=null;
    18         DataOutputStream dos=null;
    19         
    20         try {
    21             //接收来自客户端的信息
    22             in=socket.getInputStream();
    23             ois=new ObjectInputStream(in);
    24             User user= (User) ois.readObject();
    25             socket.shutdownInput();
    26             
    27             String str;
    28             if(user.getName().equals("111") && user.getPwd().equals("123")){
    29                 str="成功登陆";
    30             }else{
    31                 str="用户名或密码错误,登陆失败";
    32             }
    33             //返回给客户端的信息
    34             out=socket.getOutputStream();
    35             dos=new DataOutputStream(out);
    36             dos.writeUTF(str);
    37             socket.shutdownOutput();
    38             
    39             in.close();
    40             ois.close();
    41             dos.close();
    42             out.close();
    43             socket.close();
    44         } catch (ClassNotFoundException e) {
    45             e.printStackTrace();
    46         } catch (IOException e) {
    47             e.printStackTrace();
    48         }
    49     }
    50 }
     1 public class User implements Serializable {
     2 
     3     private static final long serialVersionUID = 4478328638580552366L;
     4     private String name;
     5     private String pwd;
     6 
     7     public String getName() {
     8         return name;
     9     }
    10 
    11     public void setName(String name) {
    12         this.name = name;
    13     }
    14 
    15     public String getPwd() {
    16         return pwd;
    17     }
    18 
    19     public void setPwd(String pwd) {
    20         this.pwd = pwd;
    21     }
    22 
    23     public User() {
    24         super();
    25     }
    26 
    27     public User(String name, String pwd) {
    28         super();
    29         this.name = name;
    30         this.pwd = pwd;
    31     }
    32 
    33     @Override
    34     public String toString() {
    35         return "User [name=" + name + ", pwd=" + pwd + "]";
    36     }
    37 
    38 }

    客户端

     1 public class Test01 {
     2     public static void main(String [] args){
     3         
     4         Scanner sc=new Scanner(System.in);
     5         System.out.println("请输入登录名:");
     6         String name=sc.nextLine();
     7         
     8         System.out.println("请输入密码:");
     9         String pwd=sc.nextLine();
    10         
    11         User user=new User(name,pwd);
    12         
    13         try {
    14             // 传输请求给服务器
    15             Socket socket=new Socket("127.0.0.1",11000);
    16             OutputStream out=socket.getOutputStream();
    17             ObjectOutputStream oos=new ObjectOutputStream(out);
    18             
    19             oos.writeObject(user);
    20             socket.shutdownOutput();
    21             
    22             //接收来自服务器的信息
    23             InputStream in=socket.getInputStream();
    24             DataInputStream dis=new DataInputStream(in);
    25             
    26             String str=dis.readUTF();
    27             System.out.println(str);
    28             
    29             
    30         } catch (UnknownHostException e) {
    31             e.printStackTrace();
    32         } catch (IOException e) {
    33             e.printStackTrace();
    34         }
    35         
    36         
    37     }
    38 }
     1 public class User implements Serializable {
     2 
     3     private static final long serialVersionUID = 4478328638580552366L;
     4     private String name;
     5     private String pwd;
     6 
     7     public String getName() {
     8         return name;
     9     }
    10 
    11     public void setName(String name) {
    12         this.name = name;
    13     }
    14 
    15     public String getPwd() {
    16         return pwd;
    17     }
    18 
    19     public void setPwd(String pwd) {
    20         this.pwd = pwd;
    21     }
    22 
    23     public User() {
    24         super();
    25     }
    26 
    27     public User(String name, String pwd) {
    28         super();
    29         this.name = name;
    30         this.pwd = pwd;
    31     }
    32 
    33     @Override
    34     public String toString() {
    35         return "User [name=" + name + ", pwd=" + pwd + "]";
    36     }
    37 
    38 }

    4.  UDP编程

    UDP编程中,如果要完成通信,通信双方必须要创建DatagramSocket,通过DatagramSocket完成通信。

    数据报包用来实现无连接包投递服务。每条报文仅根据该包中包含的信息从一台机器路由到另一台机器

    UDP步骤:

    [1]创建一个DatagramSocket用于表示发送端,通过send方法发送数据报

    [2]创建一个DatagramSocket用于表示接收端,通过receive方法接收数据报

     先运行接收端,再运行发送端!!!

    需求:完成一次单向的UDP通信。

    发送端

     1 public static void main(String[] args) {
     2 
     3         
     4 
     5          // 发送端:主动发送信息
     6 
     7          System.out.println("发送端开始发送信息...");
     8 
     9          // 【1】创建socket并指定发送数据的端口
    10 
    11          DatagramSocketsocket = null;
    12 
    13          try {
    14 
    15               socket = newDatagramSocket(8000);
    16 
    17              
    18 
    19               // 【2】创建数据报包
    20 
    21               String msg = "hello B";
    22 
    23               byte[] buf = msg.getBytes("UTF-8");
    24 
    25               DatagramPacketdp = newDatagramPacket(buf, buf.length, InetAddress.getLocalHost(), 9000);
    26 
    27              
    28 
    29               // 【3】发送
    30 
    31               socket.send(dp);
    32 
    33              
    34 
    35               // 【4】关闭
    36 
    37               socket.close();
    38 
    39          } catch (SocketExceptione) {
    40 
    41               e.printStackTrace();
    42 
    43          } catch (UnsupportedEncodingExceptione) {
    44 
    45               e.printStackTrace();
    46 
    47          } catch (UnknownHostExceptione) {
    48 
    49               e.printStackTrace();
    50 
    51          } catch (IOExceptione) {
    52 
    53               e.printStackTrace();
    54 
    55          }
    56 
    57      }

    接收端

     1 public static void main(String[] args) {
     2 
     3          // 接收端:接收信息
     4 
     5          System.out.println("启动接收端...");
     6 
     7          // 【1】创建一个DatagramSocket
     8 
     9          DatagramSocketsocket = null;
    10 
    11          try {
    12 
    13               socket = newDatagramSocket(9000);
    14 
    15               // 【2】接收消息
    16 
    17               byte[] buf = newbyte[1024];
    18 
    19               DatagramPacketdp = newDatagramPacket(buf, buf.length);
    20 
    21               System.out.println("等待接收信息...");
    22 
    23               socket.receive(dp);
    24 
    25               System.out.println("接收完成...");
    26 
    27              
    28 
    29               // 处理接收的信息
    30 
    31               String msg = new String(buf, 0, dp.getLength(), "UTF-8");
    32 
    33               System.out.println(msg);
    34 
    35              
    36 
    37          } catch (SocketExceptione) {
    38 
    39               e.printStackTrace();
    40 
    41          } catch (IOExceptione) {
    42 
    43               e.printStackTrace();
    44 
    45          }
    46 
    47      }

    需求:实现双向通信

    发送端

     1 public static void main(String[] args) {
     2 
     3         
     4 
     5          // 发送端:主动发送信息
     6 
     7          System.out.println("发送端开始发送信息...");
     8 
     9          Scanner sc = new Scanner(System.in);
    10 
    11          // 【1】创建socket并指定发送数据的端口
    12 
    13          DatagramSocketsocket = null;
    14 
    15          try {
    16 
    17               socket = newDatagramSocket(8000);
    18 
    19              
    20 
    21               for(;;) {
    22 
    23                    System.out.print("A说:");
    24 
    25                    String msg = sc.nextLine();
    26 
    27                    byte[] buf = msg.getBytes("UTF-8");
    28 
    29                    DatagramPacketdp = newDatagramPacket(buf, buf.length, InetAddress.getLocalHost(), 9000);
    30 
    31                   
    32 
    33                    // 【3】发送
    34 
    35                    socket.send(dp);
    36 
    37                   
    38 
    39                   
    40 
    41                    // 接收消息
    42 
    43                    byte[] revBuf = newbyte[1024];
    44 
    45                    DatagramPacketrevDp = newDatagramPacket(revBuf,revBuf.length);
    46 
    47                    socket.receive(revDp);
    48 
    49                    String revStr = newString(revBuf, 0, revDp.getLength(), "UTF-8");
    50 
    51                    System.out.println(dp.getAddress().getHostName()+":"+revStr);
    52 
    53               }
    54 
    55              
    56 
    57          } catch (SocketExceptione) {
    58 
    59               e.printStackTrace();
    60 
    61          } catch (UnsupportedEncodingExceptione) {
    62 
    63               e.printStackTrace();
    64 
    65          } catch (UnknownHostExceptione) {
    66 
    67               e.printStackTrace();
    68 
    69          } catch (IOExceptione) {
    70 
    71               e.printStackTrace();
    72 
    73          }finally {
    74 
    75               // 【4】关闭
    76 
    77               socket.close();
    78 
    79          }
    80 
    81      }

    接收端

     1     public static void main(String[] args) {
     2 
     3          // 接收端:接收信息
     4 
     5          System.out.println("启动接收端...");
     6 
     7          Scannersc = new Scanner(System.in);
     8 
     9          // 【1】创建一个DatagramSocket
    10 
    11          DatagramSocketsocket = null;
    12 
    13         
    14 
    15          try {
    16 
    17               socket = newDatagramSocket(9000);
    18 
    19              
    20 
    21               for(;;) {
    22 
    23                    // 接收信息
    24 
    25                    byte[] buf = newbyte[1024];
    26 
    27                    DatagramPacketdp = newDatagramPacket(buf, buf.length);
    28 
    29                    socket.receive(dp);
    30 
    31                    String msg = new String(buf, 0, dp.getLength(), "UTF-8");
    32 
    33                    System.out.println(dp.getAddress().getHostName()+":"+msg);
    34 
    35                   
    36 
    37                    // 发送信息
    38 
    39                    System.out.println("B说:");
    40 
    41                    String sendMsg = sc.nextLine();
    42 
    43                    byte[] sendBuf = sendMsg.getBytes("UTF-8");
    44 
    45                    DatagramPacketsendDp = newDatagramPacket(sendBuf, 0, sendBuf.length, dp.getAddress(), dp.getPort());
    46 
    47                    socket.send(sendDp);
    48 
    49               }
    50 
    51              
    52 
    53          } catch (SocketExceptione) {
    54 
    55               e.printStackTrace();
    56 
    57          } catch (IOExceptione) {
    58 
    59               e.printStackTrace();
    60 
    61          }finally {
    62 
    63               socket.close();
    64 
    65          }
    66 
    67      }
  • 相关阅读:
    vim的一些基本配置
    做菜好吃的小技巧02
    SQLServer创建用户登录
    Python库整理
    centos7开机界面出现多个选项
    Elasticsearch和MongoDB简要对比
    OLTP与OLAP
    CentOS7命令总结
    windows下快速删除命令
    Idea配置热部署
  • 原文地址:https://www.cnblogs.com/qq2267711589/p/10846968.html
Copyright © 2011-2022 走看看