网络编程

  • Client-Server(CS)
  • Browser/Server(BS)

1.客户端--服务端

安装客户端

  • 更新。
  • 依赖PC

2.浏览器和服务端

  • 分布式
  • 兼容性
  • 一站开发

网络通信:

  • UDP 不确定在线 不做消息确认
  • TCP可靠的通信
  • 及时通信
  • 模拟BS通信

三要素

  • IP地址:设备在网络中的地址,唯一标识
  • 端口:应用程序在设备中的唯一标识
  • 协议:数据在网络中的传输规则,常见的有UDP协议和TCP协议

IPv4:

  • 32位(4字节)
  • 点分十进制

IPv6:

  • 128位(16个字节),号称可以为地球上的每一粒沙子编号
  • 冒分十六进制

域名

  • 公网地址、私网地址(局域网使用)
  • 192.168..开头就是局域网 192.168.0.0--192.168.255.255,专门内部使用

Ip命令:

  • ipcofig:查看本机ip
  • ping IP的地址:检查网络是否连通

特殊id:

  • 127.0.0.1或者localhost:只会找本机

Ip地址操作类

InetAddress

  • public static InetAddress getLocalHost() 返回主机的ip
  • public static InetAddress getByName()得到指定的主机ip地址对象,参数是域名或者ip地址
  • public String getHostName()获取此ip地址的主机名
  • public String getHostAddress()返回ip地址的主机名
  • public boolean isReachable(int timeout)在毫秒内连通该ip地址对应的主机,连通返回true
main(){
//1.获得本机ip对象
InetAddress ip = InetAddress .getLocalHost();
//得到域名
InetAddress ip = InetAddress .getByName("www.baidu.com");
//公网的ip
InetAddress ip = InetAddress .getByName("112.82.248.76");

端口

标识在计算机上运行的程序,规定的是一个16的二进制,0-65535.

端口类型:

  • 周至端口:0-1023(HTTP:80,FTP:21)
  • 注册端口:1024-49151(Tomcat:8080,MySQL:3306)
  • 动态端口:49152-65535

协议

连接和通讯数据的规则--------网络通讯协议

  • OSI参考模型:世界互联网协议规范
  • TCP/IP参考模型:事实的国际标准

TCP:

  • 应用层

    • HTTP\FTP\DNS\SMTP
  • 传输层
    • TCP\UDP
  • 网路层
    • IP\ICMP
  • 数据链路层+物理
    • 物理寻址、比较流

传输层的协议:

  • TCP:传输控制协议
  • UCP:用户数据报协议

TCP:

  • 采用TCP协议,必须双方先建立连接,它使面向连接的可靠通信协议
  • 传输前,采用三次握手方式建立连接,所以是可靠的
  • 在连接中可以进行大数据量的传输
  • 连接、发送数据都需要确认、且传输完毕后、还要释放已建立的连接。通信效率较低

TCP协议的场景:

  • 对信息安全要求较高的场景,文件下载,金融数据通信

TCP的三次握手

  • 客户端向服务器发送请求--等待服务器确认
  • 服务器向客户端返回了一个相应--告诉客户端接受到了请求
  • 客户端向服务器再次发出确认信息---连接建立

TCP的四次挥手

  • 客户端向服务器发出取消请求
  • 服务器向客户端返回一个相应---表示收到客户端取消请求
  • 服务器向客户端发出确认消息
  • 客户端再次发出消息--连接取消

UDP:

  • 一中无连接、不可靠的传输协议
  • 将数据源ip、目的地ip、和端口封装成数据包、不需要建立连接
  • 每个数据包的大小限制在64kb内
  • 发送不管对方是否准备好,接收方也不确认,所以是不可靠的
  • 可以发送广播、发送数据结束时无需释放资源、开销小、速度快

适合语音通话、视频会话

UDP

数据包:

构造器:

  • public DatagramPacket(byte[] buf,int length, InetAddress,int port)port接受的端口
  • public DatagramPacket(byte[] buf,int length) 创建接受端的数据包 buf储存的内容 length 能接受的长度

DatagramSocket发送端和接收端对象

构造器:

  • public DatagramSocket()
  • public DatagramSocket(int port)

方法:

  • public void send( DatagramPacket dp) 发送数据包
  • public void receive( DatagramPacket p)接收数据包
main(){
DatagramSocket sock =new DatagramSocket();
//数据包
byte[] buffer ="我是韭菜".getBytes();
DatagramPacket packet =new DatagramPacket(buffer,buffer.length,InetAddress.getLocalHost(),8888);
sock.send(packet);
sock.close();
}
main(){
DatagramSocket sock =new DatagramSocket(8888);
//数据包
byte[] buffer =new byte[1024*64];
DatagramPacket packet =new DatagramPacket(buffer,buffer.length);
sock.receive(packet);
String s =new String(buffer);
socket.close();
}

多发多收

以后吧累了

TCP

面向连接,安全,可靠

java.net.Socket

Socket:

  • public Socket(String host,int port) 创建Socket对象与服务器连接,参数为服务器的ip和端口

方法:

  • OutputStream getOutputStream()获得字节输出流
  • InputStream getInputStream() 获得字节输入流
main(){
try{
//创建Socket管道建立连接
Socket socket =new Socket("127.0..0..1",7777);
//得到字节输出流
getOutputStream is =socket.getOutputStream();
//变成高级流
PrintStream ps =new PrintStream(is);
//发送消息
ps.print("约么");
ps.flush();
//socket.close();不建议关闭流
}catch(Exception e){
e.printStackTrace();
}
}

ServerSocket(服务端)

  • public ServerSocket(int port) 注册服务端
main(){
try{
//创建ServerSocket管道建立连接
ServerSocket ss =new ServerSocket(7777);
Socket socket =ss.accept();
//得到字节输出流
getInputStream is =socket.getInputStream();
//变成高级流
BufferedReader br =new BufferedReader(new InputStreamReader(is));
//收消息
while(ms=br.readLine()!=null){
System.out.print(socket.RemoteSocketAddress()+"说了"+ms)
}
//socket.close();不建议关闭流
}catch(Exception e){
e.printStackTrace();
}
}

多发多收

  • 客户端
main(){
try{
//创建Socket管道建立连接
Socket socket =new Socket("127.0..0..1",7777);
//得到字节输出流
getOutputStream is =socket.getOutputStream();
//变成高级流
PrintStream ps =new PrintStream(is);
Scanner sc =new Scanner(System.in); //发送消息
while(true){
System.out.print("请说");
String ms = sc.nextLine();
ps.println(ms);
ps.flush();
}
//socket.close();不建议关闭流
}catch(Exception e){
e.printStackTrace();
}
}

ServerSocket(服务端)

  • public ServerSocket(int port) 注册服务端
main(){
try{
//创建ServerSocket管道建立连接
ServerSocket ss =new ServerSocket(7777);
Socket socket =ss.accept();
//得到字节输出流
getInputStream is =socket.getInputStream();
//变成高级流
BufferedReader br =new BufferedReader(new InputStreamReader(is));
//收消息
while(ms=br.readLine()!=null){
System.out.print(socket.RemoteSocketAddress()+"说了"+ms);
}
//socket.close();不建议关闭流
}catch(Exception e){
e.printStackTrace();
}
}

但是服务daunt不可以接受多个客户端信息。

多客户端

  • 客户端
main(){
try{
//创建Socket管道建立连接
Socket socket =new Socket("127.0..0..1",7777);
//得到字节输出流
getOutputStream is =socket.getOutputStream();
//变成高级流
PrintStream ps =new PrintStream(is);
Scanner sc =new Scanner(System.in); //发送消息
while(true){
System.out.print("请说");
String ms = sc.nextLine();
ps.println(ms);
ps.flush();
}
//socket.close();不建议关闭流
}catch(Exception e){
e.printStackTrace();
}
}

ServerSocket(服务端)

  • public ServerSocket(int port) 注册服务端
main(){
try{
//创建ServerSocket管道建立连接
ServerSocket ss =new ServerSocket(7777);
//收消息
while(ms=br.readLine()!=null){
Socket socket =ss.accept();
new SerberThread(socket).start();
}
//socket.close();不建议关闭流
}catch(Exception e){
e.printStackTrace();
}
}

线程:

public class ServerThread extends Thread{
private Socket socket;
public ServerThread(Socket socket){
this.socket-socket;
}
@Override
public void run(){
try{
//得到字节输出流
getInputStream is =socket.getInputStream();
//变成高级流
BufferedReader br =new BufferedReader(new InputStreamReader(is));
//收消息
while(ms=br.readLine()!=null){
System.out.print(socket.RemoteSocketAddress()+"说了"+ms);
}
//socket.close();不建议关闭流
}catch{
e.printStrackTrace();
}
}
}

线程池优化

  • 客户端
main(){
try{
//创建Socket管道建立连接
Socket socket =new Socket("127.0..0..1",7777);
//得到字节输出流
getOutputStream is =socket.getOutputStream();
//变成高级流
PrintStream ps =new PrintStream(is);
Scanner sc =new Scanner(System.in); //发送消息
while(true){
System.out.print("请说");
String ms = sc.nextLine();
ps.println(ms);
ps.flush();
}
//socket.close();不建议关闭流
}catch(Exception e){
e.printStackTrace();
}
}

ServerSocket(服务端)

  • public ServerSocket(int port) 注册服务端
//定义线程池
private Static ExecutorService pool =new ThreadPoolExecutor(3,5,6,TimeUnit.SECONDS,new ArrayBlockingQueue(2,Executor.defaultThreadFactorty(),new ThreadPoolExcutor.AbortPolicy()));
main(){
try{
//创建ServerSocket管道建立连接
ServerSocket ss =new ServerSocket(7777);
//收消息
while(ms=br.readLine()!=null){
Socket socket =ss.accept();
Runner a =new SerberThread(socket);
pool.excute(a);
}
//socket.close();不建议关闭流
}catch(Exception e){
e.printStackTrace();
}
}

线程:

public class ServerThread implement Runnable{
private Socket socket;
public ServerThread(Socket socket){
this.socket-socket;
}
@Override
public void run(){
try{
//得到字节输出流
getInputStream is =socket.getInputStream();
//变成高级流
BufferedReader br =new BufferedReader(new InputStreamReader(is));
//收消息
while(ms=br.readLine()!=null){
System.out.print(socket.RemoteSocketAddress()+"说了"+ms);
}
//socket.close();不建议关闭流
}catch{
e.printStrackTrace();
}
}
}

优点:

  • 适合通信时长较短的案例

即时通讯

  • 客户端
main(){
try{
//创建Socket管道建立连接
Socket socket =new Socket("127.0..0..1",7777);
//创建一个读线程
new ClienThread(socket).start();
//得到字节输出流
getOutputStream is =socket.getOutputStream();
//变成高级流
PrintStream ps =new PrintStream(is);
Scanner sc =new Scanner(System.in); //发送消息
while(true){
System.out.print("请说");
String ms = sc.nextLine();
ps.println(ms);
ps.flush();
}
//socket.close();不建议关闭流
}catch(Exception e){
e.printStackTrace();
}
}
  • 客户端的线程

    public class ClienrThread implement Runnable{
    private Socket socket;
    public ClienThread(Socket socket){
    this.socket-socket;
    }
    @Override
    public void run(){
    try{
    //得到字节输出流
    getInputStream is =socket.getInputStream();
    //变成高级流
    BufferedReader br =new BufferedReader(new InputStreamReader(is));
    //收消息
    String line;
    while(line=br.readLine()!=null){
    System.out.print(socket.RemoteSocketAddress()+"说了"+line);
    }
    //socket.close();不建议关闭流
    }catch{
    e.printStrackTrace();
    }
    }
    }

ServerSocket(服务端)

  • public ServerSocket(int port) 注册服务端
//定义线程池
private Static ExecutorService pool =new ThreadPoolExecutor(3,5,6,TimeUnit.SECONDS,new ArrayBlockingQueue(2,Executor.defaultThreadFactorty(),new ThreadPoolExcutor.AbortPolicy()));
//客户端的留言
public static List<Socket> allSocket = new ArrayList<>();
main(){
try{
//创建ServerSocket管道建立连接
ServerSocket ss =new ServerSocket(7777);
//收消息
while(ms=br.readLine()!=null){
Socket socket =ss.accept();
allStock.add(socket);
Runner a =new SerberThread(socket);
pool.excute(a);
}
//socket.close();不建议关闭流
}catch(Exception e){
e.printStackTrace();
}
}

线程:

public class ServerThread implement Runnable{
private Socket socket;
public ServerThread(Socket socket){
this.socket-socket;
}
@Override
public void run(){
try{
//得到字节输出流
getInputStream is =socket.getInputStream();
//变成高级流
BufferedReader br =new BufferedReader(new InputStreamReader(is));
//收消息
while(ms=br.readLine()!=null){
System.out.print(socket.RemoteSocketAddress()+"说了"+ms);
sendMssageToAll(line);
}
//socket.close();不建议关闭流
}catch{
e.printStrackTrace();
}
}
private void sendMssageToAll(String msg){
for(Socket socket:ServlerThread.allSocket){
PrintStream ps =new PrintStream(socket.getOutputStream());
ps.println(msg);
ps.flush();
}
}
}

javaEE(网络编程、TCP、线程池优化)的更多相关文章

  1. java笔记--使用线程池优化多线程编程

    使用线程池优化多线程编程 认识线程池 在Java中,所有的对象都是需要通过new操作符来创建的,如果创建大量短生命周期的对象,将会使得整个程序的性能非常的低下.这种时候就需要用到了池的技术,比如数据库 ...

  2. Socket网络编程(TCP/IP/端口/类)和实例

    Socket网络编程(TCP/IP/端口/类)和实例 原文:C# Socket网络编程精华篇 转自:微冷的雨 我们在讲解Socket编程前,先看几个和Socket编程紧密相关的概念: TCP/IP层次 ...

  3. 网络编程——TCP协议、UDP协议、socket套接字、粘包问题以及解决方法

    网络编程--TCP协议.UDP协议.socket套接字.粘包问题以及解决方法 TCP协议(流式协议) ​ 当应用程序想通过TCP协议实现远程通信时,彼此之间必须先建立双向通信通道,基于该双向通道实现数 ...

  4. Socket网络编程-TCP编程

    Socket网络编程-TCP编程 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 一.socket介绍 1>.TCP/IP协议 2>.跨网络的主机间通讯 在建立通信连接的 ...

  5. Java并发编程:线程池的使用

    Java并发编程:线程池的使用 在前面的文章中,我们使用线程的时候就去创建一个线程,这样实现起来非常简便,但是就会有一个问题: 如果并发的线程数量很多,并且每个线程都是执行一个时间很短的任务就结束了, ...

  6. GO语言练习:网络编程 TCP 示例

    1.代码 2.编译及运行 1.网络编程 TCP 示例 simplehttp.go 代码 package main import ( "net" "os" &qu ...

  7. 并发编程 13—— 线程池的使用 之 配置ThreadPoolExecutor 和 饱和策略

    Java并发编程实践 目录 并发编程 01—— ThreadLocal 并发编程 02—— ConcurrentHashMap 并发编程 03—— 阻塞队列和生产者-消费者模式 并发编程 04—— 闭 ...

  8. Mysql线程池优化笔记

    Mysql线程池优化我是总结了一个站长的3篇文章了,这里我整理到一起来本文章就分为三个优化段了,下面一起来看看.     Mysql线程池系列一(Thread pool FAQ) 首先介绍什么是mys ...

  9. 网络编程TCP协议-聊天室

    网络编程TCP协议-聊天室(客户端与服务端的交互); <span style="font-size:18px;">1.客户端发数据到服务端.</span> ...

  10. Java并发编程:线程池的使用(转)

    Java并发编程:线程池的使用 在前面的文章中,我们使用线程的时候就去创建一个线程,这样实现起来非常简便,但是就会有一个问题: 如果并发的线程数量很多,并且每个线程都是执行一个时间很短的任务就结束了, ...

随机推荐

  1. Redis集群研究和实践(基于redis 3.2.5)(一)

    前言 Redis 是我们目前大规模使用的缓存中间件,由于它强大高效而又便捷的功能,得到广泛的使 用. Redis在2015年发布了3.0.0,官方支持了redis cluster.至此结束了redis ...

  2. Bugku 字符?正则?

    打开是一段中规中矩的php代码 先读一下代码 高亮文件2.php 定义变量key 定义变量IM其值是一个正则表达式匹配的结果 如果IM是真就输出key 所以这道题的关键也就是IM正则匹配的结果了,我们 ...

  3. svn 日常使用的错误集锦

    1.SVN:Previous operation has not finished; run 'cleanup' if it was interrupted 当时遇到这个问题时,找了各种解决方案什么要 ...

  4. ChatGPT能做什么?ChatGPT保姆级注册教程

    最近 OpenAI 发布的 ChatGPT 聊天机器人很火,该聊天机器人可以在模仿人类说话风格的同时回答大量的问题. 在现实世界之中,例如数字营销.线上内容创作.回答客户服务查询,甚至可以用来帮助调试 ...

  5. mouseMove模拟拖拽,封装指令

    最近项目里常常使用拖拽改变元素位置或者大小的需求,cv法文件找的脑阔疼,索性试试写一个指令. 说起指令,提一嘴,vue3没有了根元素唯一的限制后,仿佛指令绑定在组件上就不能生效了. import ty ...

  6. for循环结构、range方法

    目录 今日内容总结 whlie补充说明 for循环结构 range方法 练习 今日内容总结 whlie补充说明 1.死循环 真正死循环是一旦执行 CPU功耗会急速上升 直到系统采取紧急措施 尽量不要让 ...

  7. SQLMap入门——获取表中的字段名

    查询表名之后,查询表中的字段名 python sqlmap.py -u http://localhost/sqli-labs-master/Less-1/?id=1 -D xssplatform -T ...

  8. JavaScript:操作符:正负号和自增自减及其隐式转换数据类型

    正负号 正号即加号,负号即减号,运算结果同数学意义一样: 对非数字类型进行正负号运算,会隐式转换为数字,再进行运算: 一些特殊的非数字,转换情况同算术运算符: 自增自减 自增即为++,自减即为--. ...

  9. Windows下使用vscode连接Linux服务器进行C++代码运行与调试

    参考链接: vscode + SSH 配置 https://blog.csdn.net/irober/article/details/112724986 launch.json + tasks.jso ...

  10. Springboot启动时加载

    @Component public class SpringBootInitialization1 implements ServletContextListener { @Override publ ...