当前位置: 移动技术网 > IT编程>开发语言>Java > Java套接字(Socket)网络编程入门

Java套接字(Socket)网络编程入门

2019年07月22日  | 移动技术网IT编程  | 我要评论

网络应用模式主要有:

  • 主机/终端模式:集中计算,集中管理;
  • 客户机/服务器(client/server,简称c/s)模式:分布计算,分布管理;
  • 浏览器/服务器模式:利用internet跨平台。

www(万维网)就是建立在客户机/服务器模式上,以html语言和http协议为基础,能够提供各种internet服务的信息浏览系统。网络信息放在主机的不同位置,www服务器利用超文本链路链接各项信息。www客户机(浏览器brower)负责与服务器建立联系,向服务器发送请求,处理html超媒体,提供图形用户界面(gui),显示信息等。

在客户机/服务器工作模式中,在server端,要准备接受多个client端计算机的通信。为此,除用ip地址标识internet上的计算机之外,另还引入端口号,用端口号标识正在server端后台服务的线程。端口号与ip地址的组合称为网络套接字(socket)。

java语言在实现c/s模式中,套接字分为两类:

  1. 在server端,serversocket类支持底层的网络通信;
  2. 在client端,socket类支持网络的底层通信。

server机通过端口(总线i/o地址)提供面向client机的服务;server机在它的几个不同端口分别同时提供几种不同的服务。client接入server的某一端口,通过这个端口提请server机为其服务。规定:端口号0~1023供系统专用。例如,http协议在端口80,telnet协议在端口23。端口1024~65535供应用程序使用。

当client程序和server程序需要通信时,可以用socket类建立套接字连接。套接字连接可想象为一个电话呼叫:最初是client程序建立呼叫,server程序监听;呼叫完成后,任何一方都可以随时讲话。

双方实现通信有流式socket和数据报式socket两种可选方式:

  1. 流式socket是有连接的通信,即tcp(transmission control protocol):每次通信前建立连接,通信结束后断开连接。特点是可以保证传输的正确性、可靠性。
  2. 数据报式socket是无连接的通信,即udp(user datagram protocol):将欲传输的数据分成 小包,直接上网发送。无需建立连接和拆除连接,速度快,但无可靠保证。

流式socket在client程序和server程序间建立通信的通道。每个socket可以进行读和写两种操作。对于任一端,与对方的通信会话过程是:
建立socket连接,获得输入/输出流,读数据/写数据,通信完成后关闭socket(拆除连接)。

利用socket的构造方法,可以在客户端建立到服务器的套接字对象:
    socket(string host,int port):host是服务器的ip地址,port是端口号,这些是预先约定的。
例如,代码:

  try{
    socket mysocket = new socket(“http://www.weixueyuan.net” ,1860);
  }catch(ioexception e){}


然后,用getinputstream()方法获得输入流,用这个输入流读取服务器放入“线路”的信息;用getoutputstream()方法获得输出流,用这个输出流将信息写入“线路”。

利用serversocket的构造方法可以在服务器建立接受客户套接字的服务器套接字对象:
    serversocket(int port):指定端口号,创建一个serversocket对象。端口号port要与客户呼叫的端口号相同。为此,用以下形式代码:

  try{
    serversocket serversocket = new serversocket(1860);
  }catch(ioexception e){}


服务器端程序在指定的端口监听,当收到client程序发出的服务请求时,创建一个套接字对象与该端口对应的client程序通信。例如,执行上述建立服务器套接字对象的代码,确立了对象serversocket后,就可能它使用accept()方法,得到socket对象,接收client程序来自套接字mysocket的信息。如以下代码所示:

  try{
    socket sc = serversocket.accept();//ac是一个socket对象
  }catch(ioexception e){}


要撤销服务,可以关闭socket对象sc:

  sc.close();

【例】c/s模式中的client端应用程序。这是一个client端的流式socket通信的简单实例,代码说明client端程序的编写方法。例中,client程序向服务器主机的端口4441提出请求,连接建立后完成对服务器的读写。

import java.io.*;
import java.net.*;
public class client{
  public static void main(string args[]){
    string s = null;socket mysocket;
    datainputstream in = null;dataoutputstream out = null;
    try{
      mysocket = new socket(“localhost”,4441);
      in = new datainputstream(mysocket.getinputstream());
      out = new dataoutputstream(mysocket.getoutputstream());
      out.writeutf(“good server!”);
      while(true){
        s = in.readutf();
        if(s==null) break;
        else system.out.println(s);
      }
      mysocket.close();
    }catch(ioexception e){
      system.out.println(“can't connect”);
    }
  }
}

【例】与client端应用程序对应的server端应用程序。程序在4441端口监听,当检测到有客户机请求时,产生一个内为“客户,你好,我是服务器”的字符串输出到客户端。

import java.io.*;import java.net.*;
public class server{
  public static void main(string args[]){
    serversocket server = null;
    socket you = null;string s = null;
    dataoutputstream out = null;
    datainputstream in = null;
    try{
      server = new serversocket(4441);
    }catch(ioexception e1){
      system.out.println(“error:” +e1);
    }
    try{
      you = server.accept();
      in = new datainputstream(you.getinputstream());
      out = new dataoutputstream(you. getoutputstream());
      while(true){
        s = in.readutf();
        if(s!=null) break;
      }
      out.writeutf(“客户,你好,我是服务器”);
      out.close();
    }
    catch(ioexception e){system.out.println(“error:”+e);}
  }
}

为了充分发挥计算机的平行工作能力,可以把套接字连接工作让一个线程完成。当客户端要请求服务器给予服务,或当服务器端接收到一个客户的服务请求,就启动一个专门完成信息通信的线程,在该线程中创建输入输出流,并完成客户端与服务器端的信息交流。

【例】 将套接字连接工作置于线程的客户端小应用程序。界面在有一个发送信息按纽、一个文本框和一个文本区。客户端应用程序首先与服务器建立套接字连接。使用数据输入流in反复读取服务器放入线路里的信息,将收到的信息在文本区中显示。婐志取的信息是“结束”,则关闭套接字连接,并结束程序。用户也可在文本框输入信息,并按发送信息按钮,则客户端程序利用数据输出流out,将文本框中的内容发送给服务器。

import java.net.*;
import java.io.*;
import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
import java.applet.*;
public class aclient extends applet implements runnable,actionlistener{
  jbutton button; jtextfield textf; jtextarea texta;
  socket socket; thread thread;
  datainputstream in; dataoutputstream out;
  public void init(){
    setbackground(new color(120,153,137));
    setlayout(new borderlayout());
    button = new jbutton(“发送信息”);
    textf = new jtextfield(20);
    texta = new jtextarea(20,30);
    setsize(450,350);
    jpanel p = new jpanel();
    p.add(textf); p.add(button);
    add(texta,”center”); add(p,”south”);
    button.addactionlistener(this);
  }
  public void start(){
    try{
      socket = new socket(this.getcodebase().gethost(),4441);
      in = new datainputstream(socket.getinputstream());
      out = new dataoutputstream(socket.getoutputstream());
    }catch(ioexception e){}
    if(thread==null){
      thread = new thread(this);
      thread.setpriority(thread.min_priority);
      thread.start();
    }
  }
  public void run(){
    string s = null;
    while(true){
      try{
        s = in.readutf();
      }catch(ioexception e){}
      if(s.equals(“结束”)){
        try{
          socket.close();break;
        }catch(ioexception e){}
      }else texa.append(s + “\n”);
    }
  }
  public void actionperformed(actionevent e){
    if(e.getsource()==button){
      string s = textf.gettext();
      if(s! = null){
        try{
          out.writeutf(s);
        }catch(ioexception e1){}
      }
      else{
        try{
          out.writeutf(“请说话”);
        }
        catch(ioexception e1){}
      }
    }
  }
}

【例】程序以端4441建立与客户端的套接字连接,服务器端收到客户端的申请后,以客户的套接字建立一个线程,并启动。如果没有客户申请,则继续监听客户的申请。线程按客户的套接字建立输入数据流in和输数据流out。线程利用in读取客户放入线路里的信息。如果接受的信息是“结束”,则服务器回复“结束”后关闭套接字连接;否则回复:“我是服务器你对我说“,以及服务器接收到的信息。

import java.net.*;
import java.io.*;
import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
import java.applet.*;
public class aclient extends applet implements runnable,actionlistener{
  jbutton button; jtextfield textf; jtextarea texta;
  socket socket; thread thread;
  datainputstream in; dataoutputstream out;
  public void init(){
    setbackground(new color(120,153,137));
    setlayout(new borderlayout());
    button = new jbutton(“发送信息”);
    textf = new jtextfield(20);
    texta = new jtextarea(20,30);
    setsize(450,350);
    jpanel p = new jpanel();
    p.add(textf); p.add(button);
    add(texta,”center”); add(p,”south”);
    button.addactionlistener(this);
  }
  public void start(){
    try{
      socket = new socket(this.getcodebase().gethost(),4441);
      in = new datainputstream(socket.getinputstream());
      out = new dataoutputstream(socket.getoutputstream());
    }catch(ioexception e){}
    if(thread==null){
      thread = new thread(this);
      thread.setpriority(thread.min_priority);
      thread.start();
    }
  }
  public void run(){
    string s = null;
    while(true){
       try{
        s = in.readutf();
      }catch(ioexception e){}
      if(s.equals(“结束”)){
        try{
          socket.close();break;
        }catch(ioexception e){}
      }else texa.append(s + “\n”);
    }
  }
  public void actionperformed(actionevent e){
    if(e.getsource()==button){
      string s = textf.gettext();
      if(s! = null){
        try{
          out.writeutf(s);
        }catch(ioexception e1){}
      }
      else{
        try{
          out.writeutf(“请说话”);
        }catch(ioexception e1){}
      }
    }
  }
}

如对本文有疑问, 点击进行留言回复!!

相关文章:

验证码:
移动技术网