2023.2.6
简述HashMap的底层实现原理
HashMap是基于哈希表的Map接口的非同步实现。元素以键值对的形式存放,并且允许null键和null值,因为key值唯一(不能重复),因此,null键只有一个。另外,hashmap不保证元素存储的顺序,是一种无序的,和放入的顺序并不相同(此类不保证映射的顺序,特别是它不保证该顺序恒久不变)。HashMap是线程不安全的。
HashMap由数组(键值对entry组成的数组主干)+ 链表(元素太多时为解决哈希冲突数组的一个元素上多个entry组成的链表)+ 红黑树(当链表的元素个数达到8,且数组长度大于64时,链表存储改为红黑树存储)进行数据的存储。
HashMap采用table数组存储Key-Value的,每一个键值对组成了一个Node节点(JDK1.7为Entry实体,因为jdk1.8加入了红黑树,所以改为Node)。Node节点实际上是一个单向的链表结构,它具有Next指针,可以连接下一个Node节点,以此来解决Hash冲突的问题。
synchronized关键字有什么作用
synchronized
关键字是JAVA中常用的同步功能,提供了简单易用的锁功能。synchronized修饰普通成员方法时,被加锁的对象(即锁对象)为当前对象本身,相当于this。
synchronized修饰代码块时,括号中填入的对象就是被加锁的对象,这个对象可以是任意类型的对象。
synchronized修饰静态成员方法时,锁对象相当于是一个类对象,类对象只有一份,所以在多线程环境下是安全的。
另外一提,所有锁都是存储在Java对象头里的,Java对象头里的Mark Word里默认存储对象的HashCode,分代年龄和锁标记位。也就是说Mark Word记录了锁的状态
MySQL主从复制原理
(1) Master的更新事件(update、insert、delete)会按照顺序写入bin-log中。当Slave连接到Master的后,Master机器会为Slave开启
binlog dump线程,该线程会去读取bin-log日志
(2) Slave连接到Master后,Slave库有一个I/O线程 通过请求binlog dump thread读取bin-log日志,然后写入从库的relay log日志中。
(3) Slave还有一个 SQL线程,实时监控 relay-log日志内容是否有更新,解析文件中的SQL语句,在Slave数据库中去执行。
数据库连接池实现原理
数据库连接池(Connection pooling)是程序启动时建立足够的数据库连接,并将这些连接组成一个连接池,由程序动态地对池中的连接进行申请,使用,释放。
数据库连接池负责分配、管理、释放连接
,它保证应用程序可以重复使用同一个连接而不需要每次都建立数据库连接,如果数据库连接时间超过设置的最长数据库连接时间会自动释放链接,为了避免因为没有释放链接而导致的数据库连接遗漏,因此,数据库连接池可以明显的提高数据库的连接性能。
前台重定向与后台转发的区别
1.重定向访问服务器
两
次,转发只访问服务器一
次。2.转发页面的
URL
不会改变,而重定向地址会改变3.转发只能转发到自己的web应用内,重定向可以重定义到
任意资源路径
。4.转发相当于服务器跳转,相当于方法调用,在执行当前文件的过程中转向执行目标文件,两个文件(当前文件和目标文件)属于同一次请求,前后页
共用一个request
,可以通过此来传递一些数据或者session信息,request.setAttribute()和 request.getAttribute()。而重定向会产生一个新的request
,不能共享request域信息与请求参数5.由于转发相当于服务器内部方法调用,所以
转发后面的代码仍然会执行
(转发之后记得return);重定向代码执行之后是方法执行完成之后进行重定向操作,也就是访问第二个请求,如果是方法的最后一行进行重定向那就会马上进行重定向(重定向也需要return)。6.无论是RequestDispatcher.forward方法,还是HttpServletResponse.sendRedirect方法,在调用它们之前,都不能有内容已经被实际输出到了客户端。如果缓冲区中已经有了一些内容,这些内容将被从缓冲区中移除。
MyBatis中Mapper接口的工作原理是什么
/**
MyBatis 映射器的标记接口。
如何使用:
@Mapper
public interface UserMapper {
// ...
}
作者:
弗兰克·大卫·马丁内斯
*/
@Documented
@Inherited
@Retention(RetentionPolicy.RUNTIME)
@Target({ ElementType.TYPE, ElementType.METHOD, ElementType.FIELD, ElementType.PARAMETER })
public @interface Mapper {
// Interface Mapper
}
Spring中Bean的配置方法有那些
基于XML的配置方式
<bean id="userDao" class="cn.lovepi.***.userDao"/>
基于注解的配置方式
@Component("userDao")
public class userDao{......}
基于Java类的配置方式
@Configuration
public class ApplicationContextConfig {
@Bean
public String message() {
return "hello";
}
}
@Component:一个泛化的概念,表示一个组件(Bean),可作用在任何层次
@Controller:用于对Controller实现类进行标注,目前该功能与Component相同
@Repository:用于对DAO实现类进行标注
@Service:用于对Service实现类进行标注,目前该功能与Component相同
@Transaction的传播行为有哪些
1、REQUIRED(默认事务)
REQUIRED是常用的事务传播行为,如果当前没有事务,就新建一个事务,如果已经存在一个事务中,加入到这个事务中。
2、SUPPORTS
SUPPORTS表示当前方法不需要事务上下文,但是如果存在当前事务的话,那么这个方法会在这个事务中运行。
3、MANDATORY
MANDATORY表示该方法必须在事务中运行,如果当前事务不存在,则会抛出一个异常。不会主动开启一个事务。
4、REQUIRES_NEW
REQUIRES_NEW表示当前方法必须运行在它自己的事务中。一个新的事务将被启动,如果存在当前事务,在该方法执行期间,当前事务会被挂起(如果一个事务已经存在,则先将这个存在的事务挂起)。如果使用JTATransactionManager的话,则需要访问TransactionManager。
5、NOT_SUPPORTED
NOT_SUPPORTED表示该方法不应该运行在事务中,如果存在当前事务,在该方法运行期间,当前事务将被挂起。如果使用JTATransactionManager的话,则需要访问TransactionManager。
6、NEVER
NEVER表示当前方法不应该运行在事务上下文中,如果当前正有一个事务在运行,则会抛出异常。
7、NESTED
NESTED表示如果当前已经存在一个事务,那么该方法将会在嵌套事务中运行。嵌套的事务可以独立于当前事务进行单独地提交或回滚。如果当前事务不存在,那么其行为与REQUIRED一样。嵌套事务一个非常重要的概念就是内层事务依赖于外层事务。外层事务失败时,会回滚内层事务所做的动作。而内层事务操作失败并不会引起外层事务的回滚。
前后端分离开发中的跨域问题如何解决
前端解决
devServer: {
//是否自动打开浏览器
open: true,
//修改默认8080端口号
port: 8081,
//跨域,设置后端接口入口地址,/cxk/为代理地址必须有,为后端地址192.168.99.54,7676服务端口号
proxy: {
'/cxk/':{
target: 'http://192.168.99.54:7676/',
changeOrigin: true
}
}
},
后端解决
配置类
@SpringBootConfiguration
public class MyWebConfigurer implements WebMvcConfigurer {
/**
* 所有请求都允许跨域,使用这种配置就不需要在interceptor中配置header了
*/
@Override
public void addCorsMappings(CorsRegistry corsRegistry){
corsRegistry.addMapping("/**")
.allowCredentials(true)
.allowedOrigins("http://前端IP:端口号")
.allowedMethods("POST", "GET", "PUT", "OPTIONS", "DELETE")
.allowedHeaders("*")
.maxAge(3600);
}
}
在controller类或者下面的方法上加上@CrossOrigin注解
@RestController
@CrossOrigin
public class VisitController {
@PostMapping("/cxk/jntm")
public List<CXK> register(@RequestBody CXK cxk){
return null;
}
如何理解Spring中的IOC
控制反转
:一种设计理论思想。把对象的管理交给Spring进行,不再是原来的使用者自行管理。
DI依赖注入
:把对应属性值注入到具体对象中,如@Autowired完成属性值注入。
容器
:存储对象,使用map结构来存储,在Spring中一般存在三级缓存,singletonObjects存放完整的bean对象,整个bean的生命周期,从创建到销毁的过程都是容器来管理的。
填充属性和生命周期