Java网络编程之TCP、UDP

2014-11-25 15:23 513人阅读 评论(0) 收藏 举报
分类:
java基础及多线程(28)

版权声明:本文为博主原创文章,未经博主允许不得转载。

       Java网络编程提供了两种协议:TCP(传输控制协议)和UDP(数据报协议)。TCP(Transmission Control Protocol)是一种可靠的传输协议,传输时会采用“三次握手”端的方式建立连接,以保证数据的可靠性和安全性;而UDP(User Datagram Protocol)协议是一种不可靠的传输协议,发送的数据不一定能够接受的到,网上的聊天是工具一般采用的此协议。下面将详细的接受TCP和UDP的使 用以及相应的编码。

一、TCP网络通信
       Java中使用Socket(套接字)实现TCP。服务器端使用ServerSocket类,客户端使用Socket类实现。
     
       1、ServerSocket类
        其主要有如下的方法:
       

ServerSocket()   创建非绑定服务器套接字。
          ServerSocket(int port)  创建绑定到特定端口的服务器套接字。
        
          Socket accept()    侦听并接受到此套接字的连接。
           void close()    关闭此套接字
          boolean isClosed()   返回 ServerSocket 的关闭状态。
          InetAddress getInetAddress()    返回此服务器套接字的本地地址。
          void bind(SocketAddress endpoint)   将 ServerSocket 绑定到特定地址(IP 地址和端口号)。
          boolean isBound()   返回 ServerSocket 的绑定状态。
          SocketAddress getLocalSocketAddress()   返回此套接字绑定的端点的地址,如果尚未绑定则返回 null。
        
         服务器端每次运行是都要使用accept()方法等待客户端的连接,此方法执行之后服务器端将进入阻塞状态,知道客户端连接之后程序才继续执行,此方法返回是Socket,代表一个客户端对象。
        
       2、Socket类
       两台机器连接通信的端点。主要使用如下方法:
     
      Socket(String host, int port)  创建一个流套接字并将其连接到指定主机上的指定端口号。
      OutputStream getOutputStream()   返回此套接字的输出流。
      InputStream getInputStream()    返回此套接字的输入流。
      boolean isBound()    返回套接字的绑定状态。
      boolean isClosed()   返回套接字的关闭状态。
      boolean isConnected()     返回套接字的连接状态。
      void close()     关闭此套接字。
     其通过字节流和服务端进行通信。

实例一、下面是实现一个简单的TCP客户端可服务器端通信。
   (1)服务器端:

  1. package andy.network.test;
  2. import java.io.IOException;
  3. import java.io.PrintStream;
  4. import java.net.ServerSocket;
  5. import java.net.Socket;
  6. /**
  7. * @author Zhang,Tianyou
  8. * version:2014-11-25 上午10:49:11
  9. *
  10. *
  11. */
  12. public class FirstTCPServer {
  13. /**
  14. * @param args
  15. * @throws IOException
  16. */
  17. public static void main(String[] args) throws IOException {
  18. //创建服务器
  19. ServerSocket server = null;
  20. Socket socket = null;
  21. PrintStream out = null;
  22. //服务器在9999上等待客户端的访问
  23. server = new ServerSocket(9999);
  24. System.out.println("服务器端已经运行,等待客户的响应。。。");
  25. //程序阻塞 等待客户端的访问
  26. socket = server.accept();
  27. //向客户端输出信息
  28. String str = "hello andy.";
  29. out = new PrintStream(socket.getOutputStream());
  30. out.print(str);
  31. out.close();
  32. socket.close();
  33. server.close();
  34. }
  35. }

(2)客户端:

  1. package andy.network.test;
  2. import java.io.BufferedReader;
  3. import java.io.IOException;
  4. import java.io.InputStreamReader;
  5. import java.net.Socket;
  6. import java.net.UnknownHostException;
  7. /**
  8. * @author Zhang,Tianyou
  9. * version:2014-11-25 上午11:02:17
  10. *
  11. *
  12. */
  13. public class FirstTCPSocket {
  14. /**
  15. * @param args
  16. * @throws IOException
  17. * @throws UnknownHostException
  18. */
  19. public static void main(String[] args) throws UnknownHostException,
  20. IOException {
  21. // 定义客户端
  22. Socket client = null;
  23. // 设置地址和端口
  24. client = new Socket("localhost", 9999);
  25. BufferedReader buf = null; // 结束服务端流
  26. buf = new BufferedReader(new InputStreamReader(client.getInputStream()));
  27. String str = buf.readLine();
  28. System.out.println("服务器端通知信息:" + str);
  29. buf.close();
  30. client.close();
  31. }
  32. }

实例二
   实现客户端和服务器端的通信,服务器端可以响应多个客户端,每个客户端请求就启动一个线程。

(1)服务端

  1. package andy.network.test;
  2. import java.io.IOException;
  3. import java.net.ServerSocket;
  4. import java.net.Socket;
  5. /**
  6. * @author Zhang,Tianyou
  7. * version:2014-11-25 上午11:41:22
  8. *
  9. *         聊天服务器端
  10. */
  11. public class ChatServer {
  12. /**
  13. * @param args
  14. * @throws IOException
  15. */
  16. public static void main(String[] args) throws IOException {
  17. ServerSocket server = null;
  18. Socket client = null;
  19. // 监听9999端口的连接
  20. server = new ServerSocket(9999);
  21. boolean  flag = true;
  22. while (flag) {
  23. System.out.println("服务器运行,等待客户端连接。");
  24. client = server.accept();
  25. // 对每一个客户端请求启动一个线程
  26. new Thread(new ChatThread(client)).start();
  27. }
  28. server.close();
  29. }
  30. }

对应服务端线程任务:

  1. package andy.network.test;
  2. import java.io.BufferedReader;
  3. import java.io.InputStreamReader;
  4. import java.io.PrintStream;
  5. import java.net.Socket;
  6. /**
  7. * @author Zhang,Tianyou
  8. * version:2014-11-25 上午11:24:26
  9. *
  10. *         使用多线程机制,在每个用户响应之后启动一个新任务
  11. *
  12. */
  13. public class ChatThread implements Runnable {
  14. // 接受客户端
  15. private Socket client = null;
  16. public ChatThread(Socket client) {
  17. this.client = client;
  18. }
  19. @Override
  20. public void run() {
  21. // 向客户端发送数据
  22. PrintStream out = null;
  23. // 接收客户端发来的数据
  24. BufferedReader buff = null;
  25. try {
  26. // 得到客户端的输入信息
  27. buff = new BufferedReader(new InputStreamReader(
  28. client.getInputStream()));
  29. out = new PrintStream(client.getOutputStream());
  30. //标志是否一个客户端的操作完毕
  31. boolean flag = true;
  32. while (flag) {
  33. //不断的接收信息
  34. String str = buff.readLine();
  35. if(str == null || "".equals(str)){
  36. flag = false;//客户端操作结束
  37. }else{
  38. if("bye".equals(str)){
  39. flag = false;
  40. out.println("bye-bye");
  41. }else {
  42. //向客户端回显输入
  43. out.println("you input:" + str);
  44. }
  45. }
  46. }
  47. out.close();
  48. client.close();
  49. } catch (Exception e) {
  50. System.out.println("服务器异常!");
  51. }
  52. }
  53. }

(2)客户端

  1. package andy.network.test;
  2. import java.io.BufferedReader;
  3. import java.io.IOException;
  4. import java.io.InputStreamReader;
  5. import java.io.PrintStream;
  6. import java.net.Socket;
  7. import java.net.UnknownHostException;
  8. /**
  9. * @author Zhang,Tianyou
  10. * version:2014-11-25 上午11:53:03
  11. *
  12. *         聊天客户端程序
  13. *
  14. */
  15. public class ChatClient {
  16. public static void main(String[] args) throws UnknownHostException,
  17. IOException {
  18. Socket client = null;
  19. client = new Socket("localhost", 9999);
  20. // 接收服务器端的信息
  21. BufferedReader buff = null;
  22. // 向服务器端发送数据
  23. PrintStream out = null;
  24. BufferedReader input = null;
  25. // 获取键盘输入数据
  26. input = new BufferedReader(new InputStreamReader(System.in));
  27. out = new PrintStream(client.getOutputStream());
  28. buff = new BufferedReader(
  29. new InputStreamReader(client.getInputStream()));
  30. // 标志位
  31. boolean flag = true;
  32. while (flag) {
  33. System.out.println("输入信息:");
  34. String str = input.readLine();
  35. // 向服务器端输出信息
  36. out.println(str);
  37. if ("bye".equals(str)) {
  38. flag = false;
  39. } else {
  40. String chatCont = buff.readLine();
  41. System.out.println(chatCont);
  42. }
  43. }
  44. client.close();
  45. buff.close();
  46. }
  47. }

二、UDP网络通信
   TCP的通信是建立在可靠通信的基础上,UDP则是不可靠的通信,使用数据报形式发送数据。
   在Java中主要有DatagramPacket和DatagramSocket实现。

1、DatagramPacket主要方法
       DatagramPacket(byte[] buf, int length)
            构造 DatagramPacket,用来接收长度为 length 的数据包。
      DatagramPacket(byte[] buf, int length, InetAddress address, int port)
           构造数据报包,用来将长度为 length 的包发送到指定主机上的指定端口号。
      byte[] getData()
            返回数据缓冲区。
     int getLength()
          返回将要发送或接收到的数据的长度。

2、DatagramSocket主要方法
     DatagramSocket(int port)
            创建数据报套接字并将其绑定到本地主机上的指定端口。
     void receive(DatagramPacket p)
            从此套接字接收数据报包。
     void send(DatagramPacket p)
            从此套接字发送数据报包。
 在使用UDP时,先使用客户端指定好要接受的数据和端口。然后开启服务端发送数据。

实现如下:
(1)客户端

  1. package andy.network.test;
  2. import java.io.IOException;
  3. import java.net.DatagramPacket;
  4. import java.net.DatagramSocket;
  5. /**
  6. * @author Zhang,Tianyou
  7. * version:2014-11-25 下午3:04:10
  8. *
  9. *         UDP客户端
  10. */
  11. public class UDPClient {
  12. /**
  13. * @param args
  14. * @throws IOException
  15. */
  16. public static void main(String[] args) throws IOException {
  17. // 客户在9999端口监听
  18. DatagramSocket dSocket = null;
  19. dSocket = new DatagramSocket(9999);
  20. // 定义接收数据的字节长度
  21. byte[] buff = new byte[1024];
  22. DatagramPacket dPacket = null;
  23. // 指定接收数据的长度1024
  24. dPacket = new DatagramPacket(buff, 1024);
  25. System.out.println("等待接受数据。。");
  26. //接收数据
  27. dSocket.receive(dPacket);
  28. String str = new String(dPacket.getData(), 0, dPacket.getLength())
  29. + "from" + dPacket.getAddress().getHostAddress() + ":"
  30. + dPacket.getPort();
  31. System.out.println(str);
  32. //关闭数据报套接字
  33. dSocket.close();
  34. }
  35. }

(2)服务器端

  1. package andy.network.test;
  2. import java.io.IOException;
  3. import java.net.DatagramPacket;
  4. import java.net.DatagramSocket;
  5. import java.net.InetAddress;
  6. /**
  7. * @author Zhang,Tianyou
  8. * version:2014-11-25 下午3:13:38
  9. *
  10. * UDP服务器端
  11. *
  12. */
  13. public class UDPServer {
  14. /**
  15. * @param args
  16. * @throws IOException
  17. */
  18. public static void main(String[] args) throws IOException {
  19. DatagramSocket dSocket = null;
  20. //服务端在3333端口监听
  21. dSocket = new DatagramSocket(3333);
  22. DatagramPacket dPacket = null;
  23. //要发生的数据
  24. String str = "hello andy!";
  25. //向目标端口地址发送数据报
  26. dPacket = new DatagramPacket(str.getBytes(), str.length(),
  27. InetAddress.getByName("localhost") , 9999);
  28. System.out.println("发送数据报");
  29. dSocket.send(dPacket);
  30. dSocket.close();
  31. }
  32. }

Java网络编程之TCP、UDP的更多相关文章

  1. 4.Java网络编程之TCP/UDP

    常见传输协议: UDP , TCP UDP协议:    特点:         1.将数据及源和目的封装成数据包中,不需要建立连接         2.每个数据包的大小限制在64K内         ...

  2. Java网络编程之TCP

    Java网络编程之TCP ​ TCP主要需要两个类:Socket和ServerSocket,Socket是客户端连接服务器时创建,参数需要指定服务器的ip和端口,ServerSocket是服务器端创建 ...

  3. java网络编程之TCP通讯

    java中的网络编程之TCP协议的详细介绍,以及如何使用,同时我在下面举2例说明如何搭配IO流进行操作, /* *TCP *建立连接,形成传输数据的通道: *在连接中进行大数据量传输: *通过三次握手 ...

  4. Java网络编程之TCP通信

    一.概述 Socket类是Java执行客户端TCP操作的基础类,这个类本身使用代码通过主机操作系统的本地TCP栈进行通信.Socket类的方法会建立和销毁连接,设置各种Socket选项. Server ...

  5. 网络编程之TCP/UDP及其流程比较(转)

    TCP与UDP的区别 基于连接与无连接 对系统资源的要求(TCP较多,UDP少) UDP程序结构较简单 流模式与数据报模式TCP保证数据正确性,UDP可能丢包TCP保证数据顺序,UDP不保证 具体编程 ...

  6. java 网络编程之TCP通信和简单的文件上传功能

    */ .hljs { display: block; overflow-x: auto; padding: 0.5em; color: #333; background: #f8f8f8; } .hl ...

  7. java网络编程之TCP实例

    Dgram类 package Socket; import java.net.DatagramPacket; import java.net.InetAddress; public class Dgr ...

  8. Java网络编程之UDP

    Java网络编程之UDP 一.C/S架构中UDP网络通信流程 ①创建DatagramSocket与DatagramPacket对象 ②建立发送端,接收端 ③建立数据包 ④调用Socket的发送.接收方 ...

  9. Java网络编程之InetAddress浅析

    Java网络编程之InetAddress浅析 一.InetAddress综述 IP地址是IP使用的32位(IPv4)或者128位(IPv6)位无符号数字,它是传输层协议TCP,UDP的基础.InetA ...

随机推荐

  1. Ubunut PPA源概述

    Ubuntu 自带的“软件”应用,可以安装海量软件,既包括发行者支持的软件.社区支持的软件,也包括专有驱动和版权软件.有时,我们需要的软件通过这些渠道仍然无法找到.这时,可以到 PPA 软件源中查找. ...

  2. 【Django】视图系统

    目录 FBV 与 CBV 给视图加装饰器 使用装饰器装饰CBV 关于dispatch()方法 Request对象 与 Response对象 request对象 response对象 @ *** 一个视 ...

  3. Android手机使用WIFI及USB建立FTP服务器总结

    想必大家经常在PC和Android之间传输文件,并不是每次都会插USB接口进行文件传输,就算是插上USB接口,还是有个问题,那就是Android打开大容量存储模式之后,经常很多软件就会被强制停止使用, ...

  4. python + eclipse + django + postgresql 开发网站(一)

    一.配置开发环境 1.安装Python 载地址下:http://www.python.org/getit/

  5. 62.C++文件操作list实现内存检索,实现两千万数据秒查

    1 #include <iostream> #include <fstream> #include <cstdlib> #include <string> ...

  6. 使用Java语言开发微信公众平台(六)——获取access_token

             在前四期的文章中,我们分别学习了“环境搭建与开发接入”.“文本消息的接收与响应”.“被关注回复与关键词回复”.“图文消息的发送与响应”等环节.那么,从本篇博文开始,我们将进去更高级的 ...

  7. 修改url中某个参数

    function changeURLArg(url,arg,arg_val){ var pattern=arg+'=([^&]*)'; var replaceText=arg+'='+arg_ ...

  8. tomcat日志配置之一自带log

    问题 tomcat每次启动时,自动在logs目录下生产以下日志文件,且每天都会生成对应日期的一个文件,造成日志文件众多: localhost.2012-07-05.txt catalina.2012- ...

  9. 国内搜索大哥iOS面试题

    每一次面试之后都会对问到的面试题进行总结. 这篇总结的是我面试某大型搜索公司的iOS面试题.一面(15min)+二面(30min).并拿到实习offer.当然在今天这个特殊的节日,祝大家新年快乐.希望 ...

  10. C语言之文件操作06——写数据到文本文件遇0停止

    //文件 /* =============================================================== 题目:输入10个篮球运动员的身高数据(cm)保存至D盘文 ...