Java网络编程
Java面向网络编程实质上就是在多线程的知识基础上再引入IO流,或者也可以说是在IO流中借用多线程来达到同时操作多个流的目的。
——前言
我根据自己的学习经验总结出来经常使用的流有以下几种:
一般而言,如果我们要使用流,就必须要指定文件夹或具体的文本文件,那么我们就需要使用
File file=new File();//()中填入文件夹或文本文件的具体地址
在创建了file后我们就可以愉快地使用各种流来操作字节、字符了。
首先是文件流
FileInputStream fis=new FileInputStream(file);
FileOutputStream fos=new FileOutputStream(file);
然后是缓冲流
BufferedInputStream bis=new BufferedInputStream(file);
BufferedOutputStream bos=new BufferedOutputStream(file);
读写流(使用指定编码)
InputStreamReader isr=new InputStreamReader(new FileInputStream(file),"编码");
OutputStreamReader osr=new OutputStreamReader(new FileOutputStream(file),"编码");
读写流(不使用指定编码)
FileReader fr=new FileReader(file);
FileWriter fw=new FileWriter(file);
按行读写文本(缓冲流的一种)
BufferedReader br=new BufferedReader(new FileReader(file));//不需要指定编码
BufferedReader br=new InputStreamReader(new FileInputStream(file),"编码");//需要指定编码
打印流
PrintWriter pw=new PrintWriter(new FileWriter(file));
PrintWriter pw=new PrintWriter(new OutputStreamWriter(new FileOutputStream(file),"编码"));
基本数据类型的序列化和反序列化
DataInputStream dis=new DataInputStream(new FileInputStream(file));
DataOuputStream dos=new DataOutputStream(new FileOutputStream(file));
对象的序列化和反序列化
ObjectInputStream ois=new ObjectInputStream(new FileInputStream(file));
ObjectOutputStream oos=new ObjectOutputStream(new FileOutputStream(file));
读取控制台输入的内容
BufferedReader br=new BufferedReader(new InputStreamReader(System.in));
因为流与流中传输的内容形式和目的不尽相同,所以我们可以由此大体上分为字节流、字符流、缓冲流
如图所示:
当然上面只是对线程知识的一个复习,要想真正活用网络编程还少不了要建立一个端口来连接客户端与服务器。
import java.io.InputStream; import java.io.OutputStream; import java.io.OutputStreamWriter; import java.io.PrintWriter; import java.net.Socket; /** * 客户端 * @author Administrator * */ public class ClientDemo { public static void main(String[] args) throws Exception { //实现客户端套接字(套接字) //两台机器之间通信的端点 //本机IP127.0.0.1 localhost Socket socket=new Socket("localhost",100); //接受服务器端的内容 InputStream is=socket.getInputStream(); //输出内容到服务器端 OutputStream os=socket.getOutputStream(); //连接打印流 PrintWriter pw=new PrintWriter( new OutputStreamWriter(os)); pw.println("Hello,Java Console!"); pw.close(); socket.close(); } }
/** * 服务器端 * @author Administrator * */ public class ServerDemo { public static void main(String[] args) throws IOException { //创建服务器端实例对象 //创建服务器套接字 ServerSocket server=new ServerSocket(100); //等待客户端连接,返回Socket实例 Socket socket=server.accept(); System.out.println(socket); //接收 InputStream is=socket.getInputStream(); OutputStream os=socket.getOutputStream(); //接收客户端的内容 BufferedReader br=new BufferedReader( new InputStreamReader(is)); String str=br.readLine(); System.out.println(str); socket.close(); } }
这样一来就能够在电脑上模拟实现一个简单客户端向服务器端的信息传输了。
然而这样的网络编程是没有灵魂的,因为现实生活中不可能出现一个客户专门用一个服务器的情况(除非,嗯你懂的)
考虑到公司要恰饭,我们就必须做到一台服务器“同时”服务多个客户。
如此一来我们就不得不引入多线程。
实现多线程后的客户端和服务器端:
import java.io.IOException; import java.io.OutputStream; import java.io.OutputStreamWriter; import java.io.PrintWriter; import java.net.ServerSocket; import java.net.Socket; /** * 多线程实现服务器端 * @author Administrator * */ public class ServerThreadDemo { public void action() throws IOException{ ServerSocket server=new ServerSocket(8888); System.out.println("-----------服务器端----------"); //无限循环等待客户端连接 while(true){ Socket socket=server.accept(); //传入Socket对象到线程中 MyThread mt=new MyThread(socket); Thread t=new Thread(mt); t.start(); } } public static void main(String[] args) throws IOException { ServerThreadDemo std=new ServerThreadDemo(); std.action(); } } /** * 线程类 * @author Administrator * */ class MyThread implements Runnable{ private Socket socket; public MyThread(Socket socket){ this.socket=socket; } @Override public void run() { try { OutputStream os=socket.getOutputStream(); PrintWriter pw=new PrintWriter( new OutputStreamWriter(os)); pw.println("你好!客户端。"); pw.close(); socket.close(); } catch (IOException e) { e.printStackTrace(); } } }
import java.io.BufferedReader; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.net.Socket; /** * 多线程客户端 * @author Administrator * */ public class ClientThreadDemo { public static void main(String[] args) throws IOException{ Socket socket=new Socket("localhost",8888); System.out.println("-----------客户端----------"); InputStream is=socket.getInputStream(); BufferedReader br=new BufferedReader( new InputStreamReader(is)); String s=br.readLine(); System.out.println(s); } }
这里我偷了个懒为了让大家更好地理解加入多线程后的服务器、客户端代码,我就将实现多线程的类和服务器类写在一起了。
下面不妨通过一道简单的题来测试一下自己的知识是否已经牢固
思
考
时
间
下面展示答案
/** * 客户端 * @author Administrator */ import java.io.BufferedReader; import java.io.InputStream; import java.io.InputStreamReader; import java.io.OutputStream; import java.io.OutputStreamWriter; import java.io.PrintWriter; import java.net.Socket; public class ClientADemo { public static void main(String[] args) throws Exception{ Socket socket=new Socket("localhost",8888); OutputStream os=socket.getOutputStream(); PrintWriter pw=new PrintWriter( new OutputStreamWriter(os)); pw.println("小A"); pw.flush();//必须为flush,不能为close InputStream is=socket.getInputStream(); BufferedReader br=new BufferedReader( new InputStreamReader(is)); String s=br.readLine(); System.out.println(s); } }
/** * 线程类 * @author Administrator */ import java.io.BufferedReader; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.io.OutputStream; import java.io.OutputStreamWriter; import java.io.PrintWriter; import java.net.Socket; public class MyThread implements Runnable { private Socket socket; public MyThread(Socket socket){ this.socket=socket; } @Override public void run() { try { InputStream is=socket.getInputStream(); OutputStream os=socket.getOutputStream(); BufferedReader br=new BufferedReader( new InputStreamReader(is)); String s=br.readLine(); PrintWriter pw=new PrintWriter( new OutputStreamWriter(os)); pw.println("你好,"+s); pw.flush(); }catch (IOException e) { e.printStackTrace(); }finally{ try { socket.close(); } catch (IOException e) { e.printStackTrace(); } } } }
/** * 服务器 * @author Administrator */ import java.io.IOException; import java.net.ServerSocket; import java.net.Socket; public class ServerConsole { public static void main(String[] args) throws IOException { ServerSocket server=new ServerSocket(8888); while(true){ Socket socket=server.accept(); MyThread mt=new MyThread(socket); Thread t=new Thread(mt); t.start(); } } }
好吧我又偷了个懒为了让智慧的你留下一点展示自我的机会,我就只写出了一个ClientADemo,好了下面有请大侠一展身手!啪啪啪!!(鼓掌)
GoodNight