当前位置: 首页 > news >正文

网站开发客户的思路总结制作企业网站首页怎么做

网站开发客户的思路总结,制作企业网站首页怎么做,建设银行网站上改手机号码,保险公司官网查询面试题 1. 常见的锁策略相关的面试题 2. CAS相关的面试题 3. Synchronized 原理相关的面试题 4. Callable 接口相关的面试题 1. 常见的锁策略 乐观锁 vs 悲观锁 悲观锁: 总是假设最坏的情况,每次去拿数据的时候都认为别人会修改,所以每次在拿数据的时候都…

面试题

  • 1. 常见的锁策略
    • 相关的面试题
  • 2. CAS
    • 相关的面试题
  • 3. Synchronized 原理
    • 相关的面试题
  • 4. Callable 接口
    • 相关的面试题

1. 常见的锁策略

  1. 乐观锁 vs 悲观锁
    悲观锁: 总是假设最坏的情况,每次去拿数据的时候都认为别人会修改,所以每次在拿数据的时候都会上锁,这样别人想拿这个数据就会阻塞直到它拿到锁。
    乐观锁:
    假设数据一般情况下不会产生并发冲突,所以在数据进行提交更新的时候,才会正式对数据是否产生并发冲突进行检测,如果发现并发冲突了,则让返回用户错误的信息,让用户决定如何去做。
    Synchronized 初始使用乐观锁策略. 当发现锁竞争比较频繁的时候, 就会自动切换成悲观锁策略.

  2. 读写锁
    读写锁(readers-writer lock)看英文可以顾名思义,在执行加锁操作时需要额外表明读写意图,复数读者之间并不互斥,而写者则要求与任何人互斥。
    读写锁就是把读操作和写操作区分对待. Java 标准库提供了 ReentrantReadWriteLock 类, 实现了读写锁.

    1. ReentrantReadWriteLock.ReadLock 类表示一个读锁. 这个对象提供了 lock / unlock 方法进行加锁解锁.
    2. ReentrantReadWriteLock.WriteLock 类表示一个写锁. 这个对象也提供了 lock / unlock 方法进行加锁解锁.

    读写锁特别适合于 “频繁读, 不频繁写” 的场景中.

  3. 重量级锁 vs 轻量级锁
    操作系统基于 CPU 的原子指令, 实现了 mutex 互斥锁.JVM 又 基于操作系统提供的互斥锁, 实现了 synchronized 和 ReentrantLock 等关键字和类.
    重量级锁: 加锁机制重度依赖了 OS 提供了 mutex
    轻量级锁: 加锁机制尽可能不使用 mutex, 而是尽量在用户态代码完成. 实在搞不定了, 再使用 mutex.
    synchronized 开始是一个轻量级锁. 如果锁冲突比较严重, 就会变成重量级锁

  4. 自旋锁
    按之前的方式,线程在抢锁失败后进入阻塞状态,放弃 CPU,需要过很久才能再次被调度. 但实际上, 大部分情况下,虽然当前抢锁失败,但过不了很久,锁就会被释放。没必要就放弃 CPU. 这个时候就可以使用自旋锁来处理这样的问题.
    自旋锁伪代码: while (抢锁(lock) == 失败) {}
    如果获取锁失败, 立即再尝试获取锁, 无限循环, 直到获取到锁为止. 第一次获取锁失败, 第二次的尝试会在极短的时间内到来. 一旦锁被其他线程释放, 就能第一时间获取到锁.
    自旋锁是一种典型的 轻量级锁 的实现方式.
    优点: 没有放弃 CPU, 不涉及线程阻塞和调度, 一旦锁被释放, 就能第一时间获取到锁.
    缺点: 如果锁被其他线程持有的时间比较久, 那么就会持续的消耗 CPU 资源. (而挂起等待的时候是不消耗 CPU 的).
    synchronized 中的轻量级锁策略大概率就是通过自旋锁的方式实现的.

  5. 公平锁 vs 非公平锁
    公平锁: 遵守 “先来后到”. B 比 C 先来的. 当 A 释放锁的之后, B 就能先于 C 获取到锁.
    非公平锁: 不遵守 “先来后到”. B 和 C 都有可能获取到锁.
    注意: 操作系统内部的线程调度就可以视为是随机的. 如果不做任何额外的限制, 锁就是非公平锁. 如果要想实现公平锁, 就需要依赖额外的数据结构, 来记录线程们的先后顺序.
    synchronized 是非公平锁.

  6. 可重入锁 vs 不可重入锁
    可重入锁: 即允许同一个线程多次获取同一把锁。
    Java里只要以Reentrant开头命名的锁都是可重入锁,而且JDK提供的所有现成的Lock实现类,包括synchronized关键字锁都是可重入的。而 Linux 系统提供的 mutex 是不可重入锁.

相关的面试题

  1. 你是怎么理解乐观锁和悲观锁的,具体怎么实现呢?

悲观锁认为多个线程访问同一个共享变量冲突的概率较大, 会在每次访问共享变量之前都去真正加 锁.
乐观锁认为多个线程访问同一个共享变量冲突的概率不大. 并不会真的加锁, 而是直接尝试访问数据. 在访问的同时识别当前的数据是否出现访问冲突.
悲观锁的实现就是先加锁(比如借助操作系统提供的 mutex), 获取到锁再操作数据. 获取不到锁就等待. 乐观锁的实现可以引入一个版本号.借助版本号识别出当前的数据访问是否冲突.

  1. 介绍下读写锁?

读写锁就是把读操作和写操作分别进行加锁. 读锁和读锁之间不互斥. 写锁和写锁之间互斥. 写锁和读锁之间互斥. 读写锁最主要用在"频繁读, 不频繁写" 的场景中.

  1. 什么是自旋锁,为什么要使用自旋锁策略呢,缺点是什么?

如果获取锁失败, 立即再尝试获取锁, 无限循环, 直到获取到锁为止. 第一次获取锁失败, 第二次的尝 试会在极短的时间内到来.一旦锁被其他线程释放, 就能第一时间获取到锁.
相比于挂起等待锁,
优点: 没有放弃 CPU 资源, 一旦锁被释放就能第一时间获取到锁,更高效. 在锁持有时间比较短的场 景下非常有用.
缺点: 如果锁的持有时间较长, 就会浪费 CPU 资源

2. CAS

CAS: 全称Compare and swap,字面意思:”比较并交换“.
CAS总共分为三个步骤:

  1. 比较 A 与 V 是否相等(比较)
  2. 如果比较相等,将 B 写入 V(交换)
  3. 返回操作是否成功

当多个线程同时对某个资源进行CAS操作,只能有一个线程操作成功,但是并不会阻塞其他线程,其他线程只会收到操作失败的信号。

相关的面试题

  1. 讲解下你自己理解的 CAS 机制

全称 Compare and swap, 即 “比较并交换”. 相当于通过一个原子的操作, 同时完成 “读取内存, 比 较是否相等,修改内存” 这三个步骤. 本质上需要 CPU 指令的支撑

  1. ABA问题怎么解决?

给要修改的数据引入版本号. 在 CAS 比较数据当前值和旧值的同时, 也要比较版本号是否符合预期. 如果发现当前版本号和之前读到的版本号一致, 就真正执行修改操作, 并让版本号自增; 如果发现当 前版本号比之前读到的版本号大,就认为操作失败.

3. Synchronized 原理

结合上面的锁策略, 我们就可以总结出, Synchronized 具有以下特性(只考虑 JDK 1.8):

  1. 开始时是乐观锁, 如果锁冲突频繁, 就转换为悲观锁.
  2. 开始是轻量级锁实现, 如果锁被持有的时间较长, 就转换成重量级锁.
  3. 实现轻量级锁的时候大概率用到的自旋锁策略
  4. 是一种不公平锁
  5. 是一种可重入锁
  6. 不是读写锁

JVM 将 synchronized 锁分为 无锁、偏向锁、轻量级锁、重量级锁 状态。会根据情况,进行依次升级。
锁消除:
有些应用程序的代码中, 用到了 synchronized, 但其实没有在多线程环境下. (例如 StringBuffer)如果只是在单线程中执行这个代码, 那么这些加锁解锁操作是没有必要的, 白白浪费了一些资源开销, 这时编译器+JVM 就会判断锁是否可消除. 如果可以, 就直接消除.

相关的面试题

  1. 什么是偏向锁?

偏向锁不是真的加锁, 而只是在锁的对象头中记录一个标记(记录该锁所属的线程). 如果没有其他线 程参与竞争锁, 那么就不会真正执行加锁操作,从而降低程序开销. 一旦真的涉及到其他的线程竞 争, 再取消偏向锁状态, 进入轻量级锁状态.

4. Callable 接口

Callable 是一个 interface . 相当于把线程封装了一个 “返回值”.
使用步骤:

  1. 创建一个匿名内部类, 实现 Callable 接口. Callable 带有泛型参数. 泛型参数表示返回值的类型.
  2. 重写 Callable 的 call 方法, 完成累加的过程. 直接通过返回值返回计算结果.
  3. 把 callable 实例使用 FutureTask 包装一下.
  4. 创建线程, 线程的构造方法传入 FutureTask . 此时新线程就会执行 FutureTask 内部的 Callable 的call 方法, 完成计算. 计算结果就放到了 FutureTask 对象中.
  5. 在主线程中调用 futureTask.get() 能够阻塞等待新线程计算完毕. 并获取到 FutureTask 中的结果.

举例: 计算 1 到 1000 的值

Callable<Integer> callable = new Callable<Integer>() {@Overridepublic Integer call() throws Exception {int sum = 0;for (int i = 1; i <= 1000; i++) {sum += i;}return sum;}
};
FutureTask<Integer> futureTask = new FutureTask<>(callable);
Thread t = new Thread(futureTask);
t.start();
int result = futureTask.get();
System.out.println(result);

相关的面试题

介绍下 Callable 是什么

Callable 是一个 interface . 相当于把线程封装了一个 “返回值”.
Callable 和 Runnable 相对, 都是描述一个 “任务”. Callable 描述的是带有返回值的任务, Runnable描述的是不带返回值的任务.
Callable 通常需要搭配 FutureTask 来使用. FutureTask 用来保存 Callable 的返回结果. 因为Callable 往往是在另一个线程中执行的, 啥时候执行完并不确定. FutureTask 就可以负责这个等待结果出来的工作.

http://www.yayakq.cn/news/338368/

相关文章:

  • 《电子商务网站开发与管理》书籍html学校网站模板
  • 怎么在网上做装修网站wordpress图片主题破解版
  • 现在做网站到底需要多少钱动漫设计与制作学费
  • 建材网站做环保类型思路设计服务
  • 南京哪家公司做网站wordpress用户邮箱验证
  • 新的seo网站优化排名 网站网站做快照
  • 免费画图网站怎样建立一个企业网站
  • 手机网站建设 豆丁网站建设 佛山
  • 品牌推广网站怎么做Linux网站开发设计
  • 网站漂浮图片相册插件wordpress
  • 如何自己建设淘宝网站logo灵感网站
  • 萧山区建设局网站wordpress 文章索引
  • 产品 网站建设wordpress响应速度忽快忽慢
  • 空投糖果网站开发深圳百度seo哪家好
  • 企业网站带后台模板医院网站建设平台
  • 珠海微网站制作网站建设漂亮的模板
  • 医疗服务网站素材电脑个人网站怎么做
  • 企业网站底部企业信息网站
  • 网站群管理平台建设wordpress流量统计
  • 网站备案号怎么放互联网做视频网站需要许可证吗
  • 设计网站广告语网站美化公司
  • 跟我一起做网站化妆品网络营销策划书
  • 网站建设宣传海报南宁市网站开发
  • 烟台开发区建设业联合网站seo优化排名怎么做
  • 哈尔滨网站托管wap网站制作教程
  • 网站模板 wordpresswordpress首页名称
  • 达内网站建设佛山智家人网站
  • 蚌埠做网站公司火车头wordpress
  • 欧美 手机网站模板下载 迅雷下载 迅雷下载 迅雷下载地址三河建设厅网站
  • 南昌做网站的公司哪里好网络营销的理论基础