网络编程
- 网络通信
- 网络
- ip地址
- ipv4地址分类
- 域名
- 网络通信协议
- 网络通信协议
- TCP和UDP
InetAdress类
import java.net.InetAddress;
import java.net.UnknownHostException;
//演示INetAddress 类的使用
public class API_ {
public static void main(String[] args) {
//1.获取本机对象的 InetAddress对象
InetAddress localHost = null;
try {
localHost = InetAddress.getLocalHost();//LAPTOP-NKM8589L/192.168.10.1
} catch (UnknownHostException e) {
throw new RuntimeException(e);
}
System.out.println(localHost);
//2.根据指定的主机名,获取InetAddress对象
InetAddress byName = null;
try {
byName = InetAddress.getByName("LAPTOP-NKM8589L");
} catch (UnknownHostException e) {
throw new RuntimeException(e);
}
System.out.println("host1="+byName);
//3.根据域名返回 InetAddress对象,比如 www.baidu.com对应
InetAddress byName1 =null;
try {
byName1 = InetAddress.getByName("www.baidu.com");
} catch (UnknownHostException e) {
throw new RuntimeException(e);
}
System.out.println(byName1);
//4.通过 InetAddress 对象 获取对应的地址
String hostAddress = byName1.getHostAddress();
System.out.println("对应的ip为:"+hostAddress);
//5.通过InetAddress 对象,获取对应的主机名或者域名
String hostName = byName1.getHostName();
System.out.println("对应的域名为:"+hostName);
}
}
Socket编程
示意图
客户端和服务器端通常情况下,是在不同主机的。但是演示时,客户端和服务器端在同一主机
TCP网络通信编程
字节流
import java.io.IOException;
import java.io.OutputStream;
import java.net.InetAddress;
import java.net.Socket;
//发送hello,server给服务端
public class SocketTCP01Client {
public static void main(String[] args) throws IOException {
//1.连接服务器(ip,端口)因为是在本机监听,所以ip地址为本机地址
//连接本机的9999端口,如果连接成功,返回socket对象
Socket socket = new Socket(InetAddress.getLocalHost(),9999);
System.out.println("客户端 socket返回"+socket.getClass());
//2.连接上后,生成Socket 通过socket.getOutputStream()
//得到和socket对象关联的输出流对象
OutputStream outputStream = socket.getOutputStream();
//3.通过输出流,写入数据 到数据通道
outputStream.write("hello,server".getBytes());
//4.关闭流对象和socket,必须关闭
outputStream.close();
socket.close();
System.out.println("客户端退出");
}
}
import java.lang.String;
import jdk.internal.util.xml.impl.Input;
import java.io.IOException;
import java.io.InputStream;
import java.net.ServerSocket;
import java.net.Socket;
public class SocketTCP01Server {
public static void main(String[] args) throws IOException {
//1.在本机的9999端口监听,等待连接
// 细节:要求在本机没有其他服务在监听9999
// 细节: 这个ServerSocket 可以通过 accept() 返回多个Socket[多个客户端连接服务器的并发]
ServerSocket serverSocket = new ServerSocket(9999);
System.out.println("服务器端,在9999端口监听,等待连接...");
//2.当没有客户端连接9999端口时,程序会阻塞,等待连接
//如果有客户端连接,则会返回一个Socket对象,程序继续
Socket socket = serverSocket.accept();
System.out.println("服务端 socket="+socket.getClass());
//3.通过socket.getInputStream() 读取客户端写入到数据通道的数据,显示
InputStream inputStream = socket.getInputStream();
//4.IO读取
byte[] buf = new byte[1024];
int readLen = 0;
while ((readLen = inputStream.read(buf))!=-1){
System.out.println(new String(buf,0,readLen));
}
//5.关闭流和socket
inputStream.close();
socket.close();
serverSocket.close();
}
}
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.InetAddress;
import java.net.Socket;
//发送hello,server给服务端
public class SocketTCP02Client {
public static void main(String[] args) throws IOException {
//1.连接服务器(ip,端口)因为是在本机监听,所以ip地址为本机地址
//连接本机的9999端口,如果连接成功,返回socket对象
Socket socket = new Socket(InetAddress.getLocalHost(),9999);
System.out.println("客户端 socket返回"+socket.getClass());
//2.连接上后,生成Socket 通过socket.getOutputStream()
//得到和socket对象关联的输出流对象
OutputStream outputStream = socket.getOutputStream();
//3.通过输出流,写入数据 到数据通道
outputStream.write("hello,server".getBytes());
//设置结束标记
socket.shutdownOutput();
//1.得到输入流socket.getInputStream()
InputStream inputStream = socket.getInputStream();
byte[] buf = new byte[1024];
int readLen = 0;
while ((readLen = inputStream.read(buf))!=-1){
System.out.println(new String(buf,0,readLen));
}
//2.写入数据到数据通道
//3.关闭socket和io...
//4.关闭流对象和socket,必须关闭
outputStream.close();
socket.close();
System.out.println("客户端退出");
inputStream.close();
}
}
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.ServerSocket;
import java.net.Socket;
import java.nio.charset.StandardCharsets;
public class SocketTCP02Server {
public static void main(String[] args) throws IOException {
//1.在本机的9999端口监听,等待连接
// 细节:要求在本机没有其他服务在监听9999
// 细节: 这个ServerSocket 可以通过 accept() 返回多个Socket[多个客户端连接服务器的并发]
ServerSocket serverSocket = new ServerSocket(9999);
System.out.println("服务器端,在9999端口监听,等待连接...");
//2.当没有客户端连接9999端口时,程序会阻塞,等待连接
//如果有客户端连接,则会返回一个Socket对象,程序继续
Socket socket = serverSocket.accept();
System.out.println("服务端 socket="+socket.getClass());
//3.通过socket.getInputStream() 读取客户端写入到数据通道的数据,显示
InputStream inputStream = socket.getInputStream();
//4.IO读取
byte[] buf = new byte[1024];
int readLen = 0;
while ((readLen = inputStream.read(buf))!=-1){
System.out.println(new String(buf,0,readLen));
}
//1.得到输出流socket.getOutputStream()
OutputStream outputStream = socket.getOutputStream();
//2.写入数据到通道
outputStream.write("hello,client".getBytes());
//设置写入结束标记
socket.shutdownOutput();
//5.关闭流和socket
inputStream.close();
socket.close();
serverSocket.close();
outputStream.close();
}
}
字符流
import java.io.*;
import java.net.InetAddress;
import java.net.Socket;
//发送hello,server给服务端
public class SocketTCP03Client {
public static void main(String[] args) throws IOException {
//1.连接服务器(ip,端口)因为是在本机监听,所以ip地址为本机地址
//连接本机的9999端口,如果连接成功,返回socket对象
Socket socket = new Socket(InetAddress.getLocalHost(),9999);
System.out.println("客户端 socket返回"+socket.getClass());
//2.连接上后,生成Socket 通过socket.getOutputStream()
//得到和socket对象关联的输出流对象
OutputStream outputStream = socket.getOutputStream();
//3.通过输出流,写入数据 到数据通道,使用字符流
BufferedWriter bufferedWriter = new BufferedWriter(new OutputStreamWriter(outputStream));
bufferedWriter.write("hello,server 字符流");
bufferedWriter.newLine();//插入一个换行符,表示写入的内容结束,不需要再设置结束标记
//注意!要求对方也使用newLine()
//字符流一定要刷新,否则数据不会写入数据通道
bufferedWriter.flush();
// //设置结束标记
// socket.shutdownOutput();
//1.得到输入流socket.getInputStream(),读取数据(字符流),并显示
InputStream inputStream = socket.getInputStream();
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
String s = bufferedReader.readLine();
System.out.println(s);//输出
//2.写入数据到数据通道
//3.关闭socket和io...
//4.关闭流对象和socket,必须关闭
bufferedReader.close();//关闭外层流
bufferedWriter.close();
socket.close();
System.out.println("客户端退出");
}
}
import java.io.*;
import java.net.ServerSocket;
import java.net.Socket;
import java.nio.Buffer;
import java.nio.charset.StandardCharsets;
public class SocketTCP03Server {
public static void main(String[] args) throws IOException {
//1.在本机的9999端口监听,等待连接
// 细节:要求在本机没有其他服务在监听9999
// 细节: 这个ServerSocket 可以通过 accept() 返回多个Socket[多个客户端连接服务器的并发]
ServerSocket serverSocket = new ServerSocket(9999);
System.out.println("服务器端,在9999端口监听,等待连接...");
//2.当没有客户端连接9999端口时,程序会阻塞,等待连接
//如果有客户端连接,则会返回一个Socket对象,程序继续
Socket socket = serverSocket.accept();
System.out.println("服务端 socket="+socket.getClass());
//3.通过socket.getInputStream() 读取客户端写入到数据通道的数据,显示
InputStream inputStream = socket.getInputStream();
//4.IO读取,使用字符流,使用转换流使用 InputStreamReader 将inputStream 转换成字符流
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
String s = bufferedReader.readLine();
System.out.println(s);//输出
//1.得到输出流socket.getOutputStream()
OutputStream outputStream = socket.getOutputStream();
//2.写入数据到通道,使用字符输出流的方式回复信息
BufferedWriter bufferedWriter = new BufferedWriter(new OutputStreamWriter(outputStream));
bufferedWriter.write("hello client 字符流");
bufferedWriter.newLine();//插入一个换行符,表示回复的内容
bufferedWriter.flush();//需要手动的刷新
//5.关闭流和socket
bufferedWriter.close();
bufferedReader.close();
socket.close();
serverSocket.close();
}
}
网络上传文件
客户端也会有一个端口号,随机的端口号
import com.sun.deploy.util.StringUtils;
import java.io.*;
import java.net.InetAddress;
import java.net.Socket;
import java.net.UnknownHostException;
//文件上传的客户端
public class FileUploadClient {
public static void main(String[] args) throws Exception {
//1.连接服务器(ip,端口)
//连接本机的8888端口,如果连接成功,返回socket对象
Socket socket = new Socket(InetAddress.getLocalHost(), 8888);
//2.创建读取磁盘文件的输入流(二进制文件,不能用字节流)
String filePath = "e:\\kaola.jpg";
BufferedInputStream bis = new BufferedInputStream(new FileInputStream(filePath));
//bytes 就是文件filePath对应的字节数组
byte[] bytes = StreamUtils.streamToByteArray(bis);
//通过socket获取到输出流,将bytes数据发送给服务端
BufferedOutputStream bos = new BufferedOutputStream(socket.getOutputStream());
bos.write(bytes);//将文件对应的字节数组写入到数据通道
bis.close();
socket.shutdownOutput();//设置写入结束标记
//====接收从服务端回复的信息
InputStream inputStream = socket.getInputStream();
//使用StreamUtils方法,直接将 inputStream 读取到的内容 转成字符串
String s = StreamUtils.streamToString(inputStream);
System.out.println(s);
//关闭相关流
bos.close();
socket.close();
}
}
import java.io.*;
import java.net.ServerSocket;
import java.net.Socket;
import java.nio.Buffer;
import java.nio.charset.StandardCharsets;
//文件上传的服务端
public class TCPFileUploadServer {
public static void main(String[] args) throws Exception {
//1.服务端在本机监听8888端口
ServerSocket serverSocket = new ServerSocket(8888);
System.out.println("服务器端,在8888端口监听,等待连接");
//2.当没有客户连接8888端口时,程序会阻塞,等待连接
//如果有客户端连接,则会返回一个Socket对象,程序继续
Socket socket = serverSocket.accept();
System.out.println("服务端 socket="+socket);
//3.读取客户端发送的数据
//通过socket得到输入流
BufferedInputStream bis = new BufferedInputStream(socket.getInputStream());
byte[] bytes = StreamUtils.streamToByteArray(bis);
//4.将得到的byte 数组,写入到指定路径,就可以得到一个文件
String desFilePath = "E:\\java study\\chapter21\\untitled\\src\\kaola2.jpg";
BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(desFilePath));
bos.write(bytes);
bos.close();
//向客户端回复收到图片
//通过socket 获取收到的输出流(字符)
OutputStreamWriter writer = new OutputStreamWriter(socket.getOutputStream());
writer.write("已经收到图片");
writer.flush();//刷新,把内容刷新到数据通道
socket.shutdownOutput();//设置结束标记,
//关闭资源
bis.close();
socket.close();
serverSocket.close();
writer.close();
}
}
netstat指令
netstat -anb
可以查看tcp连接的具体情况
UDP网络编程(了解)
网络编程作业
import java.io.*;
import java.lang.String;
import java.net.ServerSocket;
import java.net.Socket;
public class Homework01Server {
public static void main(String[] args) throws IOException {
//1.监听
ServerSocket serverSocket = new ServerSocket(9999);
System.out.println("服务器端在9999端口监听,等待连接");
//2.等待
Socket socket = serverSocket.accept();
//3.通过socket.getInputStream() 读取客户端写入到服务器的数据
InputStream inputStream = socket.getInputStream();
//4.IO读取
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
String s = bufferedReader.readLine();
String answer = "";
if ("name".equals(s)){
answer = "我是nova";
}else if ("hobby".equals(s)){
answer = "编写java程序";
}else {
answer = "你说的啥子";
}
//1.得到输出流socket.getOutputStream
OutputStream outputStream = socket.getOutputStream();
//2.使用字符输出流的方式回复信息
BufferedWriter bufferedWriter = new BufferedWriter(new OutputStreamWriter(outputStream));
bufferedWriter.write(answer);
bufferedWriter.newLine();
bufferedWriter.flush();
//5.关闭流和socket
outputStream.close();
inputStream.close();
socket.close();
serverSocket.close();
}
}
import java.lang.String;
import java.io.*;
import java.net.InetAddress;
import java.net.Socket;
import java.net.UnknownHostException;
import java.util.Scanner;
public class Homework01Client {
public static void main(String[] args) throws IOException {
//1.连接服务器(ip,端口)
Socket socket = new Socket(InetAddress.getLocalHost(), 9999);
//2.连接上后,生成Socket 通过socket.getOutputStream得到和socket相关联的输出流对象
OutputStream outputStream = socket.getOutputStream();
//3.通过输出流写入数据到数据通道
BufferedWriter bufferedWriter = new BufferedWriter(new OutputStreamWriter(outputStream));
//从键盘读取用户的问题
Scanner scanner = new Scanner(System.in);
System.out.println("请输入你的问题:");
String question = scanner.next();
bufferedWriter.write(question);
bufferedWriter.newLine();//插入一个换行符,表示写入的内容结束,不需要再设置结束标记
//对方也使用readLine()
bufferedWriter.flush();//刷新
//1.得到输入流
InputStream inputStream = socket.getInputStream();
byte[] buf = new byte[1024];
int readLen = 0;
while ((readLen = inputStream.read(buf))!=-1){
System.out.println(new String(buf,0,readLen));
}
//2.写入数据到数据通道
//3.关闭socket和io...
//新写一个hobby
bufferedWriter.write("hobby");
bufferedWriter.newLine();//插入一个换行符,表示写入的内容结束,不需要再设置结束标记
//对方也使用readLine()
while ((readLen = inputStream.read(buf))!=-1){
System.out.println(new String(buf,0,readLen));
}
//4.关闭流对象和socket]
inputStream.close();
outputStream.close();
socket.close();
System.out.println("客户端退出");
}
}
import java.io.*;
import java.net.ServerSocket;
import java.net.Socket;
//先写文件下载的服务端
public class Homework02Server {
public static void main(String[] args) throws Exception {
//1.监听 9999
ServerSocket serverSocket = new ServerSocket(9999);
//2.等待客户端连接
System.out.println("服务端在9999端口监听,等待下载文件");
Socket socket = serverSocket.accept();
//3.读取 客户端发送要下载文件的名字
InputStream inputStream = socket.getInputStream();
byte[] b = new byte[1024];
int len = 0;
String downLoadFileName = "";
while ((len = inputStream.read(b)) != -1){
downLoadFileName += new String(b,0,len);
}
System.out.println("客户端希望下载文件名="+downLoadFileName);
//如果客户下载的是 三年二班 我们就返回该文件,否则返回 111.wav
String resFileName = "";
if ("三年二班".equals(downLoadFileName)){
resFileName = "E:\\java study\\chapter21\\untitled\\src\\三年二班.mp3";
}else {
resFileName = "E:\\java study\\chapter21\\untitled\\src\\111.wav";
}
//4.创建一个输入流,读取文件
BufferedInputStream bis = new BufferedInputStream(new FileInputStream(resFileName));
//5.使用工具类,读取文件到一个字节数组
byte[] bytes = StreamUtils.streamToByteArray(bis);
//6.得到socket关联的输出流
BufferedOutputStream bos =
new BufferedOutputStream(socket.getOutputStream());
//7.写入数据通道,返回给客户端
bos.write(bytes);
socket.shutdownOutput();//设置结束标记
//8.关闭相关资源
bis.close();
inputStream.close();
socket.close();
serverSocket.close();
System.out.println("服务端退出");
}
}
import java.io.*;
import java.net.InetAddress;
import java.net.Socket;
import java.net.UnknownHostException;
import java.nio.charset.StandardCharsets;
import java.util.Scanner;
//文件下载的客户端
public class Homework02Client {
public static void main(String[] args) throws Exception {
//1.接收用户输入,指定下载文件名
Scanner scanner = new Scanner(System.in);
System.out.println("请输入下载文件名:");
String downloadFileName = scanner.next();
//2.连接服务器,准备发送
Socket socket = new Socket(InetAddress.getLocalHost(), 9999);
//3.获取和Socket相关联的输出流
OutputStream outputStream = socket.getOutputStream();
outputStream.write(downloadFileName.getBytes());
//设置写入结束标志
socket.shutdownOutput();
//4.读取服务端返回的文件(字节数据)
BufferedInputStream bis = new BufferedInputStream(socket.getInputStream());
//读取文件到一个字节数组
byte[] bytes = StreamUtils.streamToByteArray(bis);
//5.得到一个输出流,写入到磁盘
String filePath ="e:\\"+downloadFileName+".mp3";
BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(filePath));
bos.write(bytes);
//6.关闭相关资源
bos.close();
bis.close();
outputStream.close();
socket.close();
System.out.println("客户端下载完毕");
}
}
项目开发流程
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-drPKpvQF-1665760177493)(E:\学习笔记\图片\Snipaste_2022-07-24_21-28-17.jpg)]
socket.shutdownOutput();
//4.读取服务端返回的文件(字节数据)
BufferedInputStream bis = new BufferedInputStream(socket.getInputStream());
//读取文件到一个字节数组
byte[] bytes = StreamUtils.streamToByteArray(bis);
//5.得到一个输出流,写入到磁盘
String filePath ="e:\\"+downloadFileName+".mp3";
BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(filePath));
bos.write(bytes);
//6.关闭相关资源
bos.close();
bis.close();
outputStream.close();
socket.close();
System.out.println("客户端下载完毕");
}
}
## 项目开发流程
![在这里插入图片描述](https://img-blog.csdnimg.cn/611cfddc8e234f85883f14bcc5865095.jpeg#pic_center)