黑马程序员——Java基础:网络编程

来源:互联网 发布:苹果下载软件快用 编辑:程序博客网 时间:2024/06/07 05:07

——-android培训、java培训、期待与您交流!  ———-

 

一、网络编程

网络编程:在java.net包中。

网络通信

      1.首先要找到对方的IP。

      2.数据要发送到对方指定的应用程序上,为了标识这些程序,所以给这些网络应用程序都用数字进行标识,为了方便称呼这个数字,我们叫做端口,逻辑端口(0~65535,其中0~1024被系统用了,或成为保留端口)。

      3.定义网络规则,这个网络规则称为协议。国际组织定义了通用协议TCP/IP。

网络通信的三要素是:IP地址,端口号,传输协议。

注:可在dos中输入:ping 127.0.0.1或ping localhost(称为:本地回环地址)来测试网卡。

        在dos中输入:ipconfig可查看本机地址。

网络参考模型:

注:通常用户操作的是应用层,而编程人员需要做的是传输层和网际层,用户在应用层操作的数据,经过逐层封包,最后到物理层发送到另一个模型中,再进行逐层解包

那么如何获取IP地址呢?

示例:获取IP

import java.net.*;class TCPAddressDemo {public static void main(String[] args) throws UnknownHostException{//获取本机地址和名称InetAddress i=InetAddress.getLocalHost();String address=i.getHostAddress();String name=i.getHostName();//获取百度地址InetAddress ia=InetAddress.getByName("www.baidu.com");String str=ia.getHostAddress();System.out.println("address:"+address+"\tname:"+name);System.out.println("address:"+str);}}

常见的传输协议

   1)UDP特点:

    1.面向无连接,即将数据及源和目的封装成数据包中,不建立链接的发送/面向无连接。

          2.每个数据包的大小限制在64K之内/数据会封包,限制在64K内。

          3.因无连接,是不可靠的协议/不可靠。

          4.不建立连接,速度快/速度快,易丢包。

    如:视频会议、聊天软件等。

   2)TCP特点:

          1.面向连接,在建立连接后,形成传输数据的通道/面向对象。

          2.在连接中进行大数据量的传输。

          3.通过三次握手完成连接,是可靠的协议。

          4.必须建立连接,效率稍慢。

    如:打电话,下载等。

注:三次握手第一次本方发送请求,第二次对方确认连接,第三次本方再次确认连接成功。

       如:找人时,A:在? B:在。A:我知道了。

二、网络传输

1)UDP传输(DatagramSecket和DatagramPacket)的步骤:

        1.创建发送器,接收器。

        2.建立数据包。

        3.调用socket的发送接收方法。

        4.关闭socket。

注:发送端和接收端是两个独立运行的程序。

其中,socket:它被称之为插座,为网络服务提供的一种机制。相当于码头,想要通信先要有港口。通信的两端都要有socket。网络通信其实就是socket之间的通信。数据在两个socket之间通过IO传输。

示例:定义一个应用程序,用于接收UDP协议传输的数据并处理

/*需求:定义一个应用程序,用于接收UDP协议传输的数据并处理思路:1.定义一个UDP的socket服务,通常会监听一个端口,就是给这个接收网络应用程序定一个数字标识,方便明确哪些数据过来该应用程序可以进行处理2.定义一个数据包,用来存储接收到的字节数据,因为数据包对象中有更多功能可以提取字节数据中的不同数据信息。3.通过socket服务的receive方法接收到的数据存入已定义好的数据包中4.通过数据包对象的特有功能,将这些不同的数据取出,打印在控制台上5.关闭资源*/import java.net.*;class UDPRece2308{public static void main(String[] args)  throws Exception{ receUDP();}//接收数据public static void receUDP()throws Exception{DatagramSocket ds=new DatagramSocket(10000);//建立接收端byte[] buf=new byte[1024];DatagramPacket dp=new DatagramPacket(buf,buf.length);//创建包,用于存储数据ds.receive(dp);//调用socket服务的接收方法,将接收到的数据存到包中//获取包中的数据信息String ip=dp.getAddress().getHostAddress();String data=new String(dp.getData(),0,dp.getLength());int port=dp.getPort();System.out.println("ip="+ip+"data="+data+"port="+port);ds.close();//关闭资源}}

先将程序打开,等待数据传过来

示例:通过UDP传输方式,将一段文字数据发送出去。

/*需求:通过UDP传输方式,将一段文字数据发送出去。思路:1.建立UDP的socket服务      2.提供数据,并将数据封装进包中      3.通过socket服务的发送功能,将数据发送出去      4.关闭资源*/import java.net.*;class UDPSend2308{public static void main(String[] args) throws Exception{ sendUDP();}//发送数据public static void sendUDP()throws Exception{DatagramSocket ds=new DatagramSocket();//建立发送端byte[] buf="Hello world".getBytes();//建立数据包DatagramPacket dp=new DatagramPacket(buf,buf.length,InetAddress.getByName("192.168.1.111"),10000);ds.send(dp);//调用socket服务的发送功能,将数据发送出去ds.close();//关闭资源}}

传输数据:

UDPRece2308接收到的数据:

练习:编写一个聊天程序。如qq

/*编写一个聊天程序。如qq有收数据部分,和发数据部分,这两部分同时执行,用到多线程udp的发送端:1:建立udp的socket服务,创建对象时如果没有明确端口,系统会自动分配一个未被使用的端口。2:明确要发送的具体数据。3:将数据封装成了数据包。4:用socket服务的send方法将数据包发送出去。5:关闭资源。udp的接收端:1:创建udp的socket服务,必须要明确一个端口,作用在于,只有发送到这个端口的数据才是这个接收端可以处理的数据。2:定义数据包,用于存储接收到数据。3:通过socket服务的接收方法将收到的数据存储到数据包中。4:通过数据包的方法获取数据包中的具体数据内容,比如ip、端口、数据等等。5:关闭资源。*/import java.io.*;import java.net.*;//发送class Send implements Runnable{private DatagramSocket ds;public Send(DatagramSocket ds){this.ds=ds;}public void run(){try{BufferedReader bufr=new BufferedReader(new InputStreamReader(System.in));String line=null;while((line=bufr.readLine())!=null){if("886".equals(line))break;byte[] buf=line.getBytes(); // 2,明确要发送的具体数据。DatagramPacket dp=new DatagramPacket(buf // 3,将数据封装成了数据包。,buf.length,InetAddress.getByName("192.168.139.1"),10010);ds.send(dp);// 4,用socket服务的send方法将数据包发送出去。}}catch (Exception e){throw new RuntimeException("发送失败");}}}//接收class Rece implements Runnable{private DatagramSocket ds;public Rece(DatagramSocket ds){this.ds=ds;}public void run(){try{while(true){byte[] buf=new byte[1024];// 2,定义数据包,用于存储接收到数据。先定义字节数组,数据包会把数据存储到字节数组中。DatagramPacket dp=new DatagramPacket(buf,buf.length);// 3,通过socket服务的接收方法将收到的数据存储到数据包中。ds.receive(dp);// 4,通过数据包的方法获取数据包中的具体数据内容,比如ip,端口,数据等等。String ip=dp.getAddress().getHostAddress();int port = dp.getPort();String data=new String(dp.getData(),0,dp.getLength());System.out.println(ip+"::"+"::"+port+"::"+data);}}catch (Exception e){throw new RuntimeException("接收失败");}}}class UDPDemo{public static void main(String[] args) throws Exception{// 1,建立udp的socket服务。DatagramSocket send=new DatagramSocket();//端口可以不指定,系统会随机分配。// 1,创建udp的socket服务。DatagramSocket rece=new DatagramSocket(10010);new Thread(new Send(send)).start();new Thread(new Rece(rece)).start();}}

2)TCP传输(Socket和ServerSocket)的步骤:

        1.创建客户端和服务器端

        2.建立连接后,通过socket中的IO流进行数据的传输

        3.关闭socket

注:同样客户端和服务器端是两个独立的应用程序。

服务端:

        服务器套接字等待请求通过网络传入。它基于该请求执行某些操作,然后可能向请求者返回结果。需监听一个端口。

         1)建立服务端的Socket服务,并监听一个端口。

         2)获取连接过来的客户对象,通过ServerSocket的accept()方法,没有连接就会等待,所以此方法是阻塞式的。

         3)客户端如果发过来数据,则服务端要使用对应的客户端对象,并获取到该客户端对象的读取流读取发过来的数据,并输出到指定目的地。

         4)关闭服务端(可选)。一般服务端是常开的,因为在实际应用中,随时有客户端在请求连接和服务。但这里需要定时关闭客户端对象流,避免某一个客户端长时间占用服务器端。

注:ServerSocket(int port,int packlog):其中backlog表示队列的最大长度,即最多连入客户端的个数,即最大连接数。

示例:定义端点接收数据并打印在控制台上

import java.io.*;import java.net.*;class TCPServerDemo2309 {public static void main(String[] args) throws IOException{//建立服务端的Socket服务,并监听一个端口ServerSocket ss=new ServerSocket(10001);//通过accept方法获取连接过来的客户端对象Socket s=ss.accept();String ip=s.getInetAddress().getHostAddress();//获取客户端发送过来的数据,通过客户端读取流的方式来读取数据InputStream in=s.getInputStream();byte[] buf=new byte[1024];int len=in.read(buf);String data=new String(buf,0,len);System.out.println("ip:"+ip+"\tdata:"+data);s.close();ss.close();}}

打开服务端:

客户端:

     通过查阅Socket对象的API文档,发现在该对象在建立时,就可去连接指定主机,因为TCP是面向连接的,所以在建立Socket服务时,就要有服务端存在,并连接成功,形成通路后,再通过该通道进行数据的传输。

      1)创建Socket服务,并指定要连接的主机端口。通路一建立,就会产生Socket流(包括输入流和输出流),通过方法获取

      2)为了发送数据,应获取Socket中的输出流,如果要接收服务端的反馈信息,还需要获取Socket的输入流

      3)通过输出流的write()方法将要发送的数据写入到流中

      4)关闭Socket流资源

注:创建Socket对象,可以创建空参数的Socket对象。如Socket s=new Socket();通过connect(SocketAddress endPoint)方法来连接到服务器。其中,SocketAddress的子类InetSocketAddress 封装了ip地址和端口。

示例:给服务器发送一个文本数据

/*需求:给服务端发送一个文本文件思路:创建socket服务,并指定要连接的主机和端口*/import java.io.*;import java.net.*;class  TCPClientDemo2309{public static void main(String[] args) throws IOException{//创建客户端socket对象,指定目的主机和端口,对象一建立,流就建立了Socket s=new Socket("192.168.1.111",10001);//获取socket流中的输出流OutputStream out=s.getOutputStream();out.write("Hello World".getBytes());s.close();}}

客户端发送数据:

服务端接收到的数据:

练习1:建立一个文本转换服务器。客户端TCPClient2313,服务端TCPServer2313。客户端给服务端发送文本,服务端会将文本转成大写再返回给客户端,而客户端可以不断的进行文本转换,可客户端输入over时,转换结束。

服务端:

分析:服务端:源:socket读取流目的:socket输出流*/import java.net.*;import java.io.*;import java.util.*;class TCPServer2313 {public static void main(String[] args) throws Exception{server(10000);}public static void server(int num)throws Exception{//接受客户端发送的信息2ServerSocket ss=new ServerSocket(num);Socket s=ss.accept();String ip=s.getInetAddress().getHostAddress();System.out.println("ip:"+ip+"-------connect");//socket读取流BufferedReader bufIn=new BufferedReader(new InputStreamReader(s.getInputStream()));//BufferedWriter bufOut=new BufferedWriter(new OutputStreamWriter(s.getOutputStream()));//可改为:PrintWriter bufOut=new PrintWriter(s.getOutputStream(),true);//true为自动刷新String line=null;while((line=bufIn.readLine())!=null){System.out.println("客户端发过来的信息:"+line);//给客户端发送信息3//bufOut.write(line.toUpperCase());//bufOut.newLine();//因为客户端的readLine()是阻塞式的,判断结束的标记是回车符//bufOut.flush();//写入到的是缓冲区中,需刷新//可改为:bufOut.println("服务端返回的数据是:"+line.toUpperCase());}ss.close();}}

打开服务端:

客户端:

分析:客户端:既然是操作设备上的数据,那么就可以使用io技术,并按照io的操作规律来思考源:键盘录入目的:设备网络,设备输出流操作的是文本数据,可以选择字符流步骤:1.建立服务  2.获取键盘录入  3.将数据发送给服务端  4.接收服务端返回的大写数据(3,4.....)  5.结束,关闭资源都是文本数据,可以使用字符流进行操作,同时提高效率,加入缓冲*/import java.net.*;import java.io.*;class TCPClient2313 {public static void main(String[] args) throws Exception{client("192.168.1.111",10000);}public static void client(String str,int num) throws Exception{Socket s=new Socket(str,num);//源:定义读取键盘数据的流对象。//读取:输进来的是字节流,要用的是字符流,所以要用InputStreamReaderBufferedReader bufr=new BufferedReader(new InputStreamReader(System.in));//目的:将数据写入到socket输出流中,发送给服务端//输出:现在的是字符流,要发送出去的是字节流,所以要用OutputStreamWriter//BufferedWriter bufOut=new BufferedWriter(new OutputStreamWriter(s.getOutputStream()));//BufferedWriter:缓冲区具有newLine();可改为:PrintWriter bufOut=new PrintWriter(s.getOutputStream(),true);//true为自动刷新//定义一个socket读取流,读取服务端返回的大写信息;BufferedReader:缓冲区具有readLine();BufferedReader bufIn=new BufferedReader(new InputStreamReader(s.getInputStream()));String line=null;while((line=bufr.readLine())!=null){if("over".equals(line))break;//发送信息到服务器端1//bufOut.write(line);//bufOut.newLine();//因为客户端的readLine()是阻塞式的,判断结束的标记是回车符//bufOut.flush();//当写入一行,写入到的是缓冲区中//可改为:bufOut.println(line);//读取服务器端发送的数据4String value=bufIn.readLine();System.out.println(value);}bufr.close();        //当socket关闭,其带有的读取流(getInputStream),关闭流(getOutputStream)也会随之关闭s.close();//当socket关闭后,readLine的结束标记为-1,所以服务端也会结束}}/*该例出现的问题现象:客户端和服务端都在莫名的等待原因是:客户端和服务端都有阻塞式方法,这些方法没有读到结束标记,就会一直等,而导致两端都在等待*/

客户端运行,传输数据并且返还的数据:

服务端接收的数据:

练习2:网络间文件复制

客户端:

分析:1.建立socket  2.将本地文件发送到服务端  源:是纯文本,用Reader,硬盘,FileReader  目的:是纯文本,用Writer,硬盘,FileWriter*/import java.net.*;import java.io.*;import java.util.*;class TCPClient2314 {public static void main(String[] args)  throws Exception{Socket s=new Socket("192.168.1.111",10001);BufferedReader bufr=new BufferedReader(new FileReader("TCPClient2313.java"));//BufferedWriter bufOut=new BufferedWriter(new OutputStreamWriter(s.getOutputStream()));//可转换成:PrintWriter bufOut=new PrintWriter(s.getOutputStream(),true);BufferedReader bufIn=new BufferedReader(new InputStreamReader(s.getInputStream()));//结束方式1:建立时间戳,来解决两边都等待的问题//long time=System.currentTimeMillis();//bufOut.println(time+"");//可改为://DataOutputStream dos=new DataOutputStream(s.getOutputStream());//long time=System.currentTimeMillis();//dos.writeLong(time);String line=null;while((line=bufr.readLine())!=null){/*bufOut.write(line);bufOut.newLine();bufOut.flush();*/bufOut.println(line);}//结束方式2:s.shutdownOutput();//关闭客户端的输出流,相当于给流中加入一个结束标记-1System.out.println(bufIn.readLine());bufr.close();s.close();}}

服务端:

分析:1.建立serversocket  2.接收客服端发送过来的文件,并保存在本机上*/import java.net.*;import java.io.*;import java.util.*;class TCPServer2314 {public static void main(String[] args)  throws Exception{ServerSocket ss=new ServerSocket(10001);Socket s=ss.accept();BufferedReader bufIn=new BufferedReader(new InputStreamReader(s.getInputStream()));String ip=s.getInetAddress().getHostAddress();System.out.println("ip:"+ip+"-------connect");//BufferedWriter bufw=new BufferedWriter(new FileWriter("D:\\TCPClick2313.java"));//可转换成:PrintWriter bufw=new PrintWriter(new FileWriter("D:\\TCPClient2313.java"),true);//BufferedWriter bufOut=new BufferedWriter(new OutputStreamWriter(s.getOutputStream()));//可转换成:PrintWriter bufOut=new PrintWriter(s.getOutputStream(),true);        /*//结束方式1:DataInputStream dis=new DataInputStream(s.getInputStream());long time=dis.readLong();//获取时间戳,然后,判断时间戳(结束标记)long currentTime=System.currentTimeMillis();System.out.println("curr:"+currentTime+"-time"+time);*/String line=null;while((line=bufIn.readLine())!=null){//if(time!=currentTime)//break;/*bufw.write(line);bufw.newLine();bufw.flush();*/bufw.println(line);}bufOut.println("发送成功!");bufw.close();s.close();ss.close();}}/*结束方式:    方法1:根据判断标记,可用判断时间戳//建立时间戳,因为时间是唯一的,来解决两边都等待的问题//long time=System.currentTimeMillis();//bufOut.println(time+"");//DataInputStream dis=new DataInputStream(s.getInputStream());//long time=dis.readLong();//获取时间戳,然后再去跟当前时间判断(结束标记)方法2:socket中的shutdownOutput()://关闭客户端的输出流,相当于给流中加入一个结束标记-1shutdownInput()*/

练习3:上传图片,并发上传图片

客户端:

分析:1.建立socket2.源:不是纯文本,字节流,硬件,FileInputStream  目的:传给服务端,不是纯文本,字节流,硬件,FileOutputStream*/import java.net.*;import java.io.*;import java.util.*;class TCPClient2401{public static void main(String[] args)  throws Exception{//给主函数传值。cmd中:java TCPClick2401 d:\1.jpgif(args.length!=1){System.out.println("请上传jpg格式图片");return;}File file=new File(args[0]);if(!(file.exists()&&file.isFile())){System.out.println("图片不存在或不是图片");return;}if(!file.getName().endsWith(".jpg")){System.out.println("请上传jpg格式的图片"+file.getName());return;}if(file.length()>1024*1024*8){System.out.println("图片太大了......");return;}Socket s=new Socket("192.168.1.111",10002);FileInputStream fin=new FileInputStream (file);        OutputStream out=s.getOutputStream();int len;byte[] buf=new byte[1024];while((len=fin.read(buf))!=-1){out.write(buf,0,len);}s.shutdownOutput();InputStream in=s.getInputStream();byte[] bufIn=new byte[1024];int num=in.read(bufIn);System.out.println(new String(bufIn,0,num));fin.close();s.close();}}

服务端:

import java.net.*;import java.io.*;import java.util.*;class TCPServer2401{public static void main(String[] args)  throws Exception{ServerSocket ss=new ServerSocket(10002);while(true){Socket s=ss.accept();new Thread(new PicThread(s)).start();}//ss.close();}public static void server() throws Exception{ServerSocket ss=new ServerSocket(10002);while (true){Socket s=ss.accept();String ip=s.getInetAddress().getHostAddress();System.out.println("ip:"+ip+"------connect");InputStream in=s.getInputStream();FileOutputStream fos=new FileOutputStream("D:\\Mine_Huan\\11.jpg");int len=0;byte[] buf=new byte[1024];while((len=in.read(buf))!=-1){fos.write(buf,0,len);}OutputStream out=s.getOutputStream();out.write("上传成功".getBytes());fos.close();s.close();}//ss.close();}}/*这个服务端有一个局限性,当A客户端连接上以后,被服务端获取到,服务端执行具体流程。这是B客户端连接,只有等待。因为服务器端还没有处理完A客户端的请求,还没有循环回来执行accept方法。所以暂时获取不到B客户端对象;那么为了让多个客户端同时并发访问服务端,服务端最好就是将每个客户端封装到一个单独的线程中,这样,就可以处理多个客户端请求了如何定义线程呢?只要明确每一个客户端要在服务端执行的代码就可,将该代码存到run方法中*///例如:客户端并发发送图片class PicThread implements Runnable{private Socket s;PicThread(Socket s){this.s=s;}public void run(){int count=1;String ip=s.getInetAddress().getHostAddress();try{System.out.println("ip:"+ip+"------connect");InputStream in=s.getInputStream();File file=new File(ip+"("+(count)+").jpg");while(file.exists()){ file=new File(ip+"("+(count++)+").jpg");}FileOutputStream fos=new FileOutputStream(file);int len=0;byte[] buf=new byte[1024];while((len=in.read(buf))!=-1){fos.write(buf,0,len);}OutputStream out=s.getOutputStream();out.write("上传成功".getBytes());fos.close();s.close();}catch (Exception e){throw new RuntimeException(ip+"出错了");}}}

练习4:客户端通过键盘录入用户名,服务端对这个用户名进行校验。如果该用户存在,在服务端显示:xxx已登陆,并在客户端显示:xxx欢迎光临。如果该用户不存在,在服务端显示:xxx尝试登陆,并在客户端显示:xxx,该用户不存在。最多就登陆三次

客户端:

import java.net.*;import java.io.*;import java.util.*;class  TCPClient2403{public static void main(String[] args)  throws Exception{Socket s=new Socket("192.168.1.111",10003);BufferedReader bufr=new BufferedReader(new InputStreamReader(System.in));OutputStream out=s.getOutputStream();PrintWriter pw=new PrintWriter(out,true);InputStream in=s.getInputStream();BufferedReader bufIn=new BufferedReader(new InputStreamReader(in));for(int i=0;i<3;i++)//最多就登陆三次{String line=bufr.readLine();if(line==null)break;pw.println(line);String info=bufIn.readLine();if(info.contains("欢迎"))break;System.out.println(info);}bufr.close();s.close();}}

服务端:

分析:1.获取客户端发送过来的信息与本地的用户文件(user2403.txt)进行比较判断*/import java.net.*;import java.io.*;import java.util.*;class Server implements Runnable{private Socket s;Server(Socket s){this.s=s;}public void run(){int count=0;String ip=s.getInetAddress().getHostAddress();System.out.println("ip:"+ip+"------connect");try{for(int i=0;i<3;i++){InputStream in=s.getInputStream();BufferedReader bufIn=new BufferedReader(new InputStreamReader(in));BufferedReader bufr=new BufferedReader(new FileReader("user2403.txt"));OutputStream out=s.getOutputStream();PrintWriter pw=new PrintWriter(out,true);String line=null;String user=bufIn.readLine();if(user==null)break;boolean flag=false;//标记while((line=bufr.readLine())!=null){if(line.equals(user)){flag=true;break;}}if(flag){System.out.println(user+"已登陆");pw.println(user+"欢迎光临");break;}else{System.out.println(user+"尝试登陆");pw.println(user+"该用户不存在");}}s.close();}catch (Exception e){throw new RuntimeException(ip+"登陆失败");}}}class  TCPServer2403{public static void main(String[] args)  throws Exception{ServerSocket ss=new ServerSocket(10003);while(true){Socket s=ss.accept();new Thread(new Server(s)).start(); }}}

练习5:客户端:浏览器,服务端:自定义

客户端:

import java.net.*;import java.io.*;import java.util.*;class  TCPClient2404{public static void main(String[] args)  throws Exception{Socket s=new Socket("192.168.1.111",10004);OutputStream out=s.getOutputStream();PrintWriter pw=new PrintWriter(out,true);pw.println("GET /JavaExercise/myhtml HTTP/1.1");//pw.println("GET /Mine_Huan/MyFile/JavaExercise/myhtml HTTP/1.1");pw.println("Accept: */*");pw.println("Accept-Language: en-US");pw.println("Host: 192.168.139.1:10004");pw.println("Connection: closed");pw.println();pw.println();BufferedReader bufIn=new BufferedReader(new InputStreamReader(s.getInputStream()));String line=null;while((line=bufIn.readLine())!=null){System.out.println(line);}s.close();}}

服务端:

import java.net.*;import java.io.*;import java.util.*;class  TCPServer2404{public static void main(String[] args) throws Exception{ServerSocket ss=new ServerSocket(10004);Socket s=ss.accept();String ip=s.getInetAddress().getHostAddress();System.out.println("ip:"+ip+"------connect");InputStream in=s.getInputStream();byte[] buf=new byte[1024];int len=in.read(buf);//读取浏览器发送过来的信息System.out.println(new String(buf,0,len));OutputStream out=s.getOutputStream();PrintWriter pw=new PrintWriter(out,true);pw.println("<font color='red' size='7'>Hello World!</font>");s.close();ss.close();}}//要先启动服务端(cmd),在浏览器中输入本机ip+访问端口即可访问服务端//如:http://192.168.139.1:10004//telnet:远程登陆命令,可以连接其它主机(相当于客户端)//如:在cmd中:telnet 192.168.139.1 10004//ip:192.168.139.1------connect/**浏览器发送过来的信息:GET /JavaExercise/myhtml HTTP/1.1Accept: text/html, application/xhtml+xml, Accept-Language: en-US,en;q=0.5User-Agent: Mozilla/5.0 (MSIE 9.0; Windows NT 6.3; WOW64; Trident/7.0; rv:11.0)like GeckoDontTrackMeHere: gzip, deflateHost: 192.168.139.1:10004DNT: 1Connection: Keep-Alive*/

 注:浏览器发送给服务器的是:”HTTP的请求消息头“信息,第一行是请求行,最后一行空行的下面是:请求数据体;对应的还有”应答请求信息“。

三、URL对象和URLConnection对象

URL:代表一个统一资源定位符,它是指向互联网“资源”的指针。即域名

方法:

       1.String getProtocol():获取协议名称

       2.String getHost():获取主机名

       3.int getPort():获取端口号

       4.String getFile():获取URL文件名

       5.String getPath():获取URL的路径部分

       6.String getQuery():获取URL的查询部,客户端传输的特定信息

注:如果URL的路径出错,会报MalformedURLException异常。

       如当IP地址为192.168.1.254,当为254时,端口号为-1,默认其端口号为:80。

URLConnection类:是一个远程连接对象

 如:URL url=new URL("http://write.blog.csdn.net/postedit/46698635");//创建URL对象

        URLConnection conn=url.openConnection();//连接指定主机,返回一个远程连接对象

        InputStream in=conn.getInputStream();

        byte[] buf=new byte[1024];

        int len=in.read(buf);

        System.out.println(buf,0,len);

小知识:

    1.如果想将主机名翻译成IP地址,需要域名解析DNS(域名解析服务器)。

  如:想登录www.sina.com.cn。需要先找DNS,通过DNS获取新浪IP地址,客户端再通过IP查找主机,但是它先要在本地主机上先查找再找DNS。

  2.http://127.0.0.1:8080和http://localhost:8080:其实127和localhost的映射关系就在本地机子上,在”c:\windows\system32\drivers\ext\host“中,修改127和localhost的映射关系,可以有效的屏蔽恶意网站。

——-android培训java培训、期待与您交流!  ———-

0 0
原创粉丝点击