线程池linux 延年有余的技术博客
发布时间:2022-11-07 12:49:48 所属栏目:Linux 来源:
导读: 简单三分钟自我介绍
自我介绍这里一笔带过,给对面介绍自己内在 + 外在 + 校园经历 + 校园项目 + 意向岗位
一面1. Java基础1.1 序列化和反序列化
首先了解一下序列化和反序列化的概念
自我介绍这里一笔带过,给对面介绍自己内在 + 外在 + 校园经历 + 校园项目 + 意向岗位
一面1. Java基础1.1 序列化和反序列化
首先了解一下序列化和反序列化的概念
简单三分钟自我介绍 自我介绍这里一笔带过,给对面介绍自己内在 + 外在 + 校园经历 + 校园项目 + 意向岗位 一面1. Java基础1.1 序列化和反序列化 首先了解一下序列化和反序列化的概念 序列化:将Java对象以二进制即字节码的形式保存在磁盘文件中,可以说是保存Java对象状态的过程,序列化可以实现对象保存的持久化; 反序列化:将保存在磁盘文件中的Java字节码重新转换为Java对象的过程; 其他特点:一般RPC框架底层协议通信就是通过序列化和反序列化在网络上传输Java对象。 序列化和反序列化的实现主要有两种,准确来说有三种方法: 采用默认的序列化方式,即通过ObjectOutPutStream类的writeObject(OutputStream out)方法来序列化到输出流中 输出流可以选择文件流、也可以选择管道流,甚至是二进制流 文件流是直接写到文件中再读取转成对象,管道流是通过管道缓存数据,然后再通过输入流连接管道读取转成对象 序列化的对象必须实现Seriablized接口,才能完成序列化和反序列化操作 class Student implements Serializable { private String name; private Integer age; } //FileOutputStream fos = new FileOutputStream("D:\\student.txt"); PipedOutputStream pos = new PipedOutputStream(); PipedInputStream pis = new PipedInputStream(); pis.connect(pos); ObjectOutputStream oos = new ObjectOutputStream(pos); Student student = new Student(); student.setAge(21); student.setName("zs"); oos.writeObject(student); //FileInputStream fis = new FileInputStream("D:\\student.txt"); ObjectInputStream ois = new ObjectInputStream(pis); Student res = (Student) ois.readObject(); System.out.println(res); // 自定义协议 比如我可以将加入对象头 cafe babe private void readObject(ObjectInputStream in) throws IOException, ClassNotFoundException { System.out.println("自定义反序列化"); int magic = in.readInt(); this.name = (String) in.readObject(); this.age = (Integer) in.readObject(); } // 自定义协议 比如我可以将加入对象头 cafe babe private void writeObject(ObjectOutputStream out) throws IOException { System.out.println("自定义序列化"); // 4 字节 魔数 out.writeInt(0xCAFEBABE); out.writeObject(this.name); out.writeObject(this.age); } 实现接口Externalizable并重写方法,其实跟第二种差别不大,只是第二种有默认的私有方法 @Override public void writeExternal(ObjectOutput out) throws IOException { System.out.println("实现 Externalizable 接口的自定义序列化"); out.writeObject(this.name); out.writeObject(this.age); } @Override public void readExternal(ObjectInput in) throws IOException, ClassNotFoundException { System.out.println("实现 Externalizable 接口的自定义反序列化"); this.name = (String) in.readObject(); this.age = (Integer) in.readObject(); } 解决反序列化破坏单例 解决反射破坏单例 反射创建对象根本也是要调用构造方法,而且可以无视构造方法的访问修饰符(public、private) 1.2 说一说数据类型有哪些 Java有八种基本数据类型 + String 1个位的bit,布尔类型的boolean,2个字节的short,4个字节的int、char,8个字节的long、double、float 其中基本类型中的包装类型常用的有Integer、Long 其中Integer会自动进行拆封装处理,也就是可以直接跟int类型比较数值上的大小 底层在-128-127之间会做缓存,在这之间通过Integer.valueOf(int)创建的对象都是同一个,使用了享元设计模式 System.out.println(new Integer(1) == 1); System.out.println(Integer.valueOf(1) == Integer.valueOf(1)); System.out.println(Integer.valueOf(128) == Integer.valueOf(128)); 结果 true true false 1.3 数据结构 给你你个浏览器,要求设计前进和后退的数据结构,优先考虑性能 那么由于浏览器前进后退访问,是一种FIFO的结构,比如你连续点击前进几个页面,最先进的页面最后返回,即LIFO 那么可以考虑栈的结构设计,栈结构设计要考虑性能,首先我们可以分析到,浏览器页面跳转没有涉及到页面的修改,即用于查询 那么优先考虑数组而不考虑链表 我们可以设计两个栈数组,一个用于入栈已前进的页面,一个用于入栈已后退的页面,取其中一个栈顶元素作为当前页面 2. MySQL2.1 索引 在MySQL中,直接影响索引类型的是数据库的存储引擎 使用MyIsam存储引擎,数据文件和索引是分开的,索引会另外存储在另一个文件中 使用InnoDB存储引擎,数据和索引都存储在同一个文件中,而且是以B+数的数据结构存储,非叶子节点存储索引,叶子节点存储索引和索引对应的数据 就MyIsam引擎来说,索引中最主要的是聚簇索引,也就是主键的默认索引 单值索引和多值索引,这里是指组合索引,好的组合索引可以达到覆盖索引,可以做到避免回表,这里是因为叶子节点通过覆盖索引带了数据,因为B+树只有叶子节点带有数据,非叶子节点都是索引 而多个组合索引下,有效索引要做到左匹配,也就是必须从左顺序匹配到右查询,否则索引将失效 2.2 口述 sql 给你一张表,有三个字段,id、产品id、备注信息,现在需要你查询相同产品id的记录,然后id值相同的记录数大于等于5的产品id 首先呢,我们可以先定义这张表为S 因为涉及相同字段的记录,可以考虑直接分组,使用聚合函数 select pro_id from S group by pro_id having count(pro_id) >= 5 3. JVM3.1 线程的死锁了解过吗? 比如有两个线程t1和t2,t1线程有资源r1,t2有资源r2,t1线程执行代码中需要资源r2,不过这段代码需要t2线程把资源r2释放才能执行,此时t2线程也执行代码中,释放资源前需要获取资源r1,但t2又需要r2,此时处于相互等待的状态,就导致了死锁。 从Java角度来说,资源相当于Java的锁对象,是互斥的,一个线程获取锁对象后,另一个线程只能等待,t1线程获取锁对象r1,也就是占有了锁r1,这时线程t2也是占有了锁对象r2,而线程t1需要获取锁对象r2才能往下执行代码,使得线程t1阻塞,而线程t2处于阻塞等待锁对象r1释放,才能释放锁对象r2,这样就导致死锁。(互相等待) 4. JUC4.1 线程池有了解过吗? 线程池主要有核心线程数、救急线程和队列,队列分为阻塞队列和非阻塞队列。 目前线程池主要可以分为几类: 只有核心线程、无救急线程的线程池,此时等待队列中有要执行的任务,而核心线程在轮询地执行等待队列中的任务,如果队列满或者队列是无界队列,可能导致内存溢出问题。 一般这种线程池的做法就是使用了拒绝策略,拒绝策略可分为直接丢弃新任务、异常抛出(主动逻辑处理)、丢弃等待队列头结点、提交任务线程执行。 最后一个是推荐使用的 只有救急线程的线程池,这种的话有线程池newCachedThreadPool,它能无限创建救急线程,队列采用SynchronousQueue ,是一个没有容量的队列,只有线程取任务时才能提交任务; 最后是一种核心线程数只有1的线程池,没有救急线程,任务队列无界,一般作为单线程任务,这样就不会有CPU的轮询切换,任务的执行效率最高,不过请求数太多的情况下,也是容易导致内存溢出。 非阻塞队列实现的有CurrentLinkedQueue,它是通过CAS无锁化机制的线程池队列,每个线程通过for(;;)执行,是一个单向且通过GC自动回收出队节点的,利用可达性算法分析,将next指向自己线程池linux,即可触发延迟回收,利用元素的不可重用性,规避ABA问题 5. Linux 给你一个日志文件,要求你查询最近一天内中,匹配到关键字的所有记录数据 一般日志实时查询可以使用该命令,它会实时更新,而且会处于fg模式,tail打印文件末尾记录,也就是最近 tail -100f catalina.log | grep "关键字" 而使用cat是查询历史,只能打印日志到屏幕 比如按照tail或head来查询关键字为20:的后5条数据并显示行号 cat -n log.log4j | grep "20:" | tail -n 5 时间段查询 grep '2022-08-21 20:1[1-9]' log.log4j 综合使用 cat -n log.log4j | grep -E "关键字|2022-08-21 20:1[0-9]" | tail -n 10 (编辑:拼字网 - 核心网) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |
站长推荐