为什么现在BAT面试必问分布式?阿里大牛带你实战剖析分布式锁

面试官:讲一下什么是负载均衡,什么是轮询策略、随机策略、哈希策略 本文已收录GitHub,更有互联网大厂面试真题,面试攻略,高效学习资料等 什么是负载均衡? 先举个例子吧。以超市收银为例,假设现在只有一个窗口、一个收银员: 一般情况下,收银员平均 2 分钟服务一位顾客,10 分钟可以服务 5 位顾客; 到周末高峰期时,收银员加快收银,平均 1 分钟服务一位顾客,10 分钟最多服务 10 位顾客,也就是说一个顾客最多等待 10 分钟; 逢年过节,顾客数量激增,一下增加到 30 位顾客,如果仍然只有一个窗口和一个收银员,那么所有顾客就只能排队等候了,一个顾客最多需要等待. 阅读详情

本文已收录GitHub,更有互联网大厂面试真题,面试攻略,高效学习资料等

为什么要使用分布锁?

首先,我先带你认识一下什么是锁。

在单机多线程环境中,我们经常遇到多个线程访问同一个共享资源(这里需要注意的是:在很多地方,这种资源会称为临界资源,但在今天这篇文章中,我们统一称之为共享资源)的情况。为了维护数据的一致性,我们需要某种机制来保证只有满足某个条件的线程才能访问资源,不满足条件的线程只能等待,在下一轮竞争中重新满足条件时才能访问资源。

这个机制指的是,为了实现分布式互斥,在某个地方做个标记,这个标记每个线程都能看到,到标记不存在时可以设置该标记,当标记被设置后,其他线程只能等待拥有该标记的线程执行完成,并释放该标记后,才能去设置该标记和访问共享资源。这里的标记,就是我们常说的锁。

也就是说,锁是实现多线程同时访问同一共享资源,保证同一时刻只有一个线程可访问共享资源所做的一种标记。

与普通锁不同的是,分布式锁是指分布式环境下,系统部署在多个机器中,实现多进程分布式互斥的一种锁。为了保证多个进程能看到锁,锁被存在公共存储(比如 Redis、Memcache、数据库等三方存储中),以实现多个进程并发访问同一个临界资源,同一时刻只有一个进程可访问共享资源,确保数据的一致性。

那什么场景下需要使用分布式锁呢?

比如,现在某电商要售卖某大牌吹风机(以下简称“吹风机”),库存只有 2 个,但有 5个来自不同地区的用户{A,B,C,D,E}几乎同时下单,那么这 2 个吹风机到底会花落谁家呢?

你可能会想,这还不简单,谁先提交订单请求,谁就购买成功呗。但实际业务中,为了高并发地接受大量用户订单请求,很少有电商网站真正实施这么简单的措施。

此外,对于订单的优先级,不同电商往往采取不同的策略,比如有些电商根据下单时间判断谁可以购买成功,而有些电商则是根据付款时间来判断。但,无论采用什么样的规则去判断谁能购买成功,都必须要保证吹风机售出时,数据库中更新的库存是正确的。为了便于理解,我在下面的讲述中,以下单时间作为购买成功的判断依据。

我们能想到的最简单方案就是,给吹风机的库存数加一个锁。当有一个用户提交订单后,后台服务器给库存数加一个锁,根据该用户的订单修改库存。而其他用户必须等到锁释放以后,才能重新获取库存数,继续购买。

在这里,吹风机的库存就是共享资源,不同的购买者对应着多个进程,后台服务器对共享资源加的锁就是告诉其他进程“关键重地,非请勿入”。

但问题就这样解决了吗?当然没这么简单。

想象一下,用户 A 想买 1 个吹风机,用户 B 想买 2 个吹风机。在理想状态下,用户 A 网速好先买走了 1 个,库存还剩下 1 个,此时应该提示用户 B 库存不足,用户 B 购买失败。但实际情况是,用户 A 和用户 B 同时获取到商品库存还剩 2 个,用户 A 买走 1 个,在用户 A 更新库存之前,用户 B 又买走了 2 个,此时用户 B 更新库存,商品还剩 0 个。这时,电商就头大了,总共 2 个吹风机,却卖出去了 3 个。

不难看出,如果只使用单机锁将会出现不可预知的后果。因此,在高并发场景下,为了保证临界资源同一时间只能被一个进程使用,从而确保数据的一致性,我们就需要引入分布式锁了。

此外,在大规模分布式系统中,单个机器的线程锁无法管控多个机器对同一资源的访问,这时使用分布式锁,就可以把整个集群当作一个应用一样去处理,实用性和扩展性更好。

分布式锁的三种实现方法及对比

接下来,我带你看看实现分布式锁的 3 种主流方法,即:

  • 基于数据库实现分布式锁,这里的数据库指的是关系型数据库;
  • 基于缓存实现分布式锁;
  • 基于 ZooKeeper 实现分布式锁。

基于数据库实现分布式锁

要实现分布式锁,最简单的方式就是创建一张锁表,然后通过操作该表中的数据来实现。

当我们要锁住某个资源时,就在该表中增加一条记录,想要释放锁的时候就删除这条记录。数据库对共享资源做了唯一性约束,如果有多个请求被同时提交到数据库的话,数据库会保证只有一个操作可以成功,操作成功的那个线程就获得了访问共享资源的锁,可以进行操作。

基于数据库实现的分布式锁,是最容易理解的。但是,因为数据库需要落到硬盘上,频繁读取数据库会导致 IO 开销大,因此这种分布式锁适用于并发量低,对性能要求低的场景。对于双 11、双 12 等需求量激增的场景,数据库锁是无法满足其性能要求的。而在平日的购物中,我们可以在局部场景中使用数据库锁实现对资源的互斥访问。

下面,我们还是以电商售卖吹风机的场景为例。吹风机库存是 2 个,有 5 个来自不同地区的用户{A,B,C,D,E}想要购买,其中用户 A 想买 1 个,用户 B 想买 2 个,用户 C 想买 1个。

用户 A 和用户 B 几乎同时下单,但用户 A 的下单请求最先到达服务器。因此,该商家的产品数据库中增加了一条关于用户 A 的记录,用户 A 获得了锁,他的订单请求被处理,服务器修改吹风机库存数,减去 1 后还剩下 1 个。

当用户 A 的订单请求处理完成后,有关用户 A 的记录被删除,服务器开始处理用户 B 的订单请求。这时,库存只有 1 个了,无法满足用户 B 的订单需求,因此用户 B 购买失败。

从数据库中,删除用户 B 的记录,服务器开始处理用户 C 的订单请求,库存中 1 个吹风机满足用户 C 的订单需求。所以,数据库中增加了一条关于用户 C 的记录,用户 C 获得了锁,他的订单请求被处理,服务器修改吹风机数量,减去 1 后还剩下 0 个。

可以看出,基于数据库实现分布式锁比较简单,绝招在于创建一张锁表,为申请者在锁表里建立一条记录,记录建立成功则获得锁,消除记录则释放锁。该方法依赖于数据库,主要有两个缺点:

  • 单点故障问题。一旦数据库不可用,会导致整个系统崩溃。
  • 死锁问题。数据库锁没有失效时间,未获得锁的进程只能一直等待已获得锁的进程主动释放锁。一旦已获得锁的进程挂掉或者解锁操作失败,会导致锁记录一直存在数据库中,其他进程无法获得锁。

基于缓存实现分布式锁

数据库的性能限制了业务的并发量,那么对于双 11、双 12 等需求量激增的场景是否有解决方法呢?

基于缓存实现分布式锁的方式,非常适合解决这种场景下的问题。所谓基于缓存,也就是说把数据存放在计算机内存中,不需要写入磁盘,减少了 IO 读写。接下来,我以 Redis 为例与你展开这部分内容。

Redis 通常可以使用 setnx(key, value) 函数来实现分布式锁。key 和 value 就是基于缓存的分布式锁的两个属性,其中 key 表示锁 id,value = currentTime + timeOut,表示当前时间 + 超时时间。也就是说,某个进程获得 key 这把锁后,如果在 value 的时间内未释放锁,系统就会主动释放锁。

setnx 函数的返回值有 0 和 1:

  • 返回 1,说明该服务器获得锁,setnx 将 key 对应的 value 设置为当前时间 + 锁的有效时间。
  • 返回 0,说明其他服务器已经获得了锁,进程不能进入临界区。该服务器可以不断尝试setnx 操作,以获得锁。

我还是以电商售卖吹风机的场景为例,和你说明基于缓存实现的分布式锁,假设现在库存数量是足够的。

用户 A 的请求因为网速快,最先到达 Server2,setnx 操作返回 1,并获取到购买吹风机的锁;用户 B 和用户 C 的请求,几乎同时到达了 Server1 和 Server3,但因为这时 Server2获取到了吹风机数据的锁,所以只能加入等待队列。

Server2 获取到锁后,负责管理吹风机的服务器执行业务逻辑,只用了 1s 就完成了订单。订单请求完成后,删除锁的 key,从而释放锁。此时,排在第二顺位的 Server1 获得了锁,可以访问吹风机的数据资源。但不巧的是,Server1 在完成订单后发生了故障,无法主动释放锁。

于是,排在第三顺位的 Server3 只能等设定的有效时间(比如 30 分钟)到期,锁自动释放后,才能访问吹风机的数据资源,也就是说用户 C 只能到 00:30:01 以后才能继续抢购。

总结来说,Redis 通过队列来维持进程访问共享资源的先后顺序。Redis 锁主要基于 setnx函数实现分布式锁,当进程通过 setnx<key,value> 函数返回 1 时,表示已经获得锁。排在后面的进程只能等待前面的进程主动释放锁,或者等到时间超时才能获得锁。

相对于基于数据库实现分布式锁的方案来说,基于缓存实现的分布式锁的优势表现在以下几个方面:

  • 性能更好。数据被存放在内存,而不是磁盘,避免了频繁的 IO 操作。
  • 很多缓存可以跨集群部署,避免了单点故障问题。
  • 很多缓存服务都提供了可以用来实现分布式锁的方法,比如 Redis 的 setnx 方法等。
  • 可以直接设置超时时间来控制锁的释放,因为这些缓存服务器一般支持自动删除过期数据。

这个方案的不足是,通过超时时间来控制锁的失效时间,并不是十分靠谱,因为一个进程执行时间可能比较长,或受系统进程做内存回收等影响,导致时间超时,从而不正确地释放了锁。

为了解决基于缓存实现的分布式锁的这些问题,我们再来看看基于 ZooKeeper 实现的分布式锁吧。

基于ZooKeeper实现分布式锁

ZooKeeper 基于树形数据存储结构实现分布式锁,来解决多个进程同时访问同一临界资源时,数据的一致性问题。ZooKeeper 的树形数据存储结构主要由 4 种节点构成:

  • 持久节点。这是默认的节点类型,一直存在于 ZooKeeper 中。
  • 持久顺序节点。也就是说,在创建节点时,ZooKeeper 根据节点创建的时间顺序对节点进行编号。
  • 临时节点。与持久节点不同,当客户端与 ZooKeeper 断开连接后,该进程创建的临时节点就会被删除。
  • 临时顺序节点,就是按时间顺序编号的临时节点。

根据它们的特征,ZooKeeper 基于临时顺序节点实现了分布锁。

还是以电商售卖吹风机的场景为例。假设用户 A、B、C 同时在 11 月 11 日的零点整提交了购买吹风机的请求,ZooKeeper 会采用如下方法来实现分布式锁:

  1. 在与该方法对应的持久节点 shared_lock 的目录下,为每个进程创建一个临时顺序节点。如下图所示,吹风机就是一个拥有 shared_lock 的目录,当有人买吹风机时,会为他创建一个临时顺序节点。
  2. 每个进程获取 shared_lock 目录下的所有临时节点列表,注册子节点变更的Watcher,并监听节点。
  3. 每个节点确定自己的编号是否是 shared_lock 下所有子节点中最小的,若最小,则获得锁。例如,用户 A 的订单最先到服务器,因此创建了编号为 1 的临时顺序节点LockNode1。该节点的编号是持久节点目录下最小的,因此获取到分布式锁,可以访问临界资源,从而可以购买吹风机。
  4. 若本进程对应的临时节点编号不是最小的,则分为两种情况:
  • 本进程为读请求,如果比自己序号小的节点中有写请求,则等待;
  • 本进程为写请求,如果比自己序号小的节点中有读请求,则等待。

例如,用户 B 也想要买吹风机,但在他之前,用户 C 想看看吹风机的库存量。因此,用户B 只能等用户 A 买完吹风机、用户 C 查询完库存量后,才能购买吹风机。

可以看到,使用 ZooKeeper 可以完美解决设计分布式锁时遇到的各种问题,比如单点故障、不可重入、死锁等问题。虽然 ZooKeeper 实现的分布式锁,几乎能涵盖所有分布式锁的特性,且易于实现,但需要频繁地添加和删除节点,所以性能不如基于缓存实现的分布式锁。

三种实现方式对比

我通过一张表格来对比一下这三种方式的特点,以方便你理解、记忆。

总结来说,ZooKeeper 分布式锁的可靠性最高,有封装好的框架,很容易实现分布式锁的功能,并且几乎解决了数据库锁和缓存式锁的不足,因此是实现分布式锁的首选方法。

从上述分析可看出,为了确保分布式锁的可用性,我们在设计时应考虑到以下几点:

互斥性,即在分布式系统环境下,分布式锁应该能保证一个资源或一个方法在同一时间只
能被一个机器的一个线程或进程操作。
具备锁失效机制,防止死锁。即使有一个进程在持有锁的期间因为崩溃而没有主动解锁,
也能保证后续其他进程可以获得锁。
可重入性,即进程未释放锁时,可以多次访问临界资源。
有高可用的获取锁和释放锁的功能,且性能要好。

总结

本文以电商购物为例,首先带你剖析了什么是分布式锁,以及为什么需要分布式锁;然后,与你介绍了三种实现分布式锁的方法,包括基于数据库实现、基于缓存实现(以 Redis 为例),以及基于 ZooKeeper 实现。

分布式锁是解决多个进程同时访问临界资源的常用方法,在分布式系统中非常常见,比如开源的 ZooKeeper、Redis 中就有所涉及。通过今天这篇文章对分布式锁原理及方法的讲解,我相信你会发现分布式锁不再那么神秘、难懂,然后以此为基础对分布式锁进行更深入的学习和应用。

接下来,我把今天的内容通过下面的一张思维导图再全面总结下。

阿里架构师一文详解微内核架构,原来微内核这么简单 本文已收录GitHub,更有互联网大厂面试真题,面试攻略,高效学习资料等 微内核架构(Microkernel Architecture),也被称为插件化架构(Plug-inArchitecture),是一种面向功能进行拆分的可扩展性架构,通常用于实现基于产品(原文为 product-based,指存在多个版本、需要下载安装才能使用,与 web-based 相对应)的应用。例如 Eclipse 这类 IDE 软件、UNIX 这类操作系统、淘宝 App 这类客户端软件等,也有一些企业将自己的业务系统设计成.. 阅读详情

相关推荐

面试官:请比较一下SpringCloud与Dubbo

一、Dubbo 1. Dubbo简介 Dubbo是阿里巴巴公司开源的一个高性能优秀的服务框架,使得应用可通过高性能的RPC实现服务的输出和输入功能,可以和Spring框架无缝集成。 Dubbo是一款高性能、轻量级的开源Java RPC框架,它提供了三大核心能力:面向接口的远程方法调用,智能容错和负载均衡,以及服务自动注册和发现。 现已发展成为Apache的顶级孵化开源项目,详见官网: 2. Dub...

Java_Cappuccino的博客 1674

一个项目部署多个节点会导致锁失效么_为什么现在BAT面试必问分布式?阿里大牛带你实战剖析分布式锁...

本文已收录GitHub,更有互联网大厂面试真题,面试攻略,高效学习资料等为什么要使用分布锁?首先,我先带你认识一下什么是锁。在单机多线程环境中,我们经常遇到多个线程访问同一个共享资源(这里需要注意的是:在很多地方,这种资源会称为临界资源,但在今天这篇文章中,我们统一称之为共享资源)的情况。为了维护数据的一致性,我们需要某种机制来保证只有满足某个条件的线程才能访问资源,不满足条件的线程只能等待,在下...

weixin_39702649的博客 109

NVIDIA驱动版本太低?手把手教你解决CUDA与PyTorch版本冲突问题

本文针对深度学习开发中常见的NVIDIA驱动版本过低导致的CUDA与PyTorch版本冲突问题,提供了从根源理解到实战解决的完整指南。文章详细解析了驱动、CUDA与PyTorch的依赖关系,并给出了升级驱动、降级PyTorch、使用Conda环境管理及Docker容器化四种核心解决方案,帮助开发者快速诊断并构建稳定的GPU开发工作流。

grpc6streamer的博客 970

腾讯阿里美团相继搞事,渣本程序员的出路在哪?

10月份美团在内网通报最新的职级体系调整,明年初起实行新的“扁平职级,宽带薪酬”体系,原有的“M+P”双职级线、“1-2 至 3-3”等专业序列被取消,取而代之的是以“L+数字”命名的单...

HollisChuang's Blog 886

STM32项目分享:智能家居语音系统

(资料分享见文末)基于STM32的智能家居语音系统温湿度采集:系统通过DHT11模块采集温湿度烟雾监测:通过MQ-2模块采集环境中烟雾浓度光照强度采集:通过BH1750传感器采集环境光照强度窗帘控制:通过步进电机转动模拟窗帘控制风扇控制:通过继电器和指示灯模拟风扇驱动照明控制:通过继电器和指示灯模拟照明驱动蜂鸣器报警:环境烟雾异常情况下蜂鸣器报警OLED显示:显示温湿度、光照强度和烟雾浓度APP功能:使用机智云APP,包括功能有控制照明灯和风扇开关、显示当前温湿度信息。

qq_44016222的博客 4146

STM32在六轴机械臂实时控制中的选型与分层架构设计

嵌入式实时控制系统中,微控制器的选型直接决定运动控制精度与系统可靠性。其核心在于匹配确定性中断响应、低延迟外设协同与工业协议栈支持等硬性指标。STM32凭借Cortex-M内核的NVIC调度能力、成熟HAL库及CAN FD/高级定时器等专用外设,在机电一体化场景中成为伺服控制中枢的首选。相比ESP32等通用MCU,STM32在硬实时性、EMC认证生态和工业总线兼容性上具备不可替代优势。本文围绕GTB六轴机械臂项目,详解基于STM32F407的硬件抽象层配置、FreeRTOS任务调度、事件队列解耦及闭环控制数

jupi8的博客 755

影响几十万程序员的决策,腾讯阿里美团又搞事了。。。

10月份美团在内网通报最新的职级体系调整,明年初起实行新的“扁平职级,宽带薪酬”体系,原有的“M+P”双职级线、“1-2 至 3-3”等专业序列被取消,取而代之的是以“L+数字”命名的单...

weixin_44421461的博客 296

Qt+PCL实战:如何用QVTKOpenGLNativeWidget高效渲染3D点云(附完整代码)

本文深入解析了Qt与PCL结合使用QVTKOpenGLNativeWidget进行高效3D点云渲染的实战技术。通过对比传统QVTKWidget,详细介绍了QVTKOpenGLNativeWidget在渲染效率、内存占用和兼容性方面的显著优势,并提供了完整的代码示例和性能优化策略,助力开发者在工业检测、自动驾驶等领域实现更高效的点云可视化。

keras9composer的博客 687

请求支援Java!腾讯阿里美团相继搞事,渣本直接被掀翻在地。。。

10月份美团在内网通报最新的职级体系调整,明年初起实行新的“扁平职级,宽带薪酬”体系,原有的“M+P”双职级线、“1-2 至 3-3”等专业序列被取消,取而代之的是以“L+数字”命名的单...

欢迎关注公众号:【码农突围】,回复9999,可以获取一份LeetCode刷题笔记 402

计算机毕设:线性回归 Xgboost LSTM 预测黄金价格实战 完整代码数据视频讲解 可直接运行

线性回归 Xgboost LSTM 预测黄金价格实战 完整代码数据视频讲解 可直接运行

1761

基于STM32的智能婴儿床设计(蓝牙通信+摄像头监控)_315

本项目设计并实现了一款基于STM32微控制器的智能婴儿床系统,通过多种传感器和智能控制模块为家长提供更便捷和高效的婴儿照护解决方案。系统包括婴儿哭泣检测、湿度监测、空气质量检测、温度监控等多项功能,并通过蓝牙与手机APP进行数据传输和远程控制。婴儿床内置摇摇床和安抚音乐播放功能,能够在婴儿哭泣时自动启动摇摇床并播放安抚音乐。此外,系统还支持摄像头远程监控,让家长实时查看婴儿的状态。整个系统采用STM32F103RCT6作为核心控制单元,结合声音传感器、湿度传感器、MQ135空气质量传感器。

865

2019Java程序员唯一学习指南,决战BAT

做了3~5年Java开发,你已经积累了不少项目经验,扩宽了技术广度,也许已发力成为团队管理者。到了这个阶段,大家却常有这种感受:感觉自己卡在瓶颈进步缓慢,技术水平很难像早期一样实现大幅突破? 其实大家往往忽略了这一点——提升自己的架构认知(工作5年左右的Java程序员必须重视架构认知的提升,这会很大程度上推动你今后的成长)。 架构的本质在...

weixin_34310785的博客 101

【GlobalMapper精品教程】027:路径剖面和和视线工具的使用

路径剖面视线工具允许您使用加载的高程数据集沿用户指定的路径获取垂直剖面。要定义生成3D路径剖面所遵循的路径,只需单击鼠标左键选择路径的点,然后石键单击以结束路径。出现一个带有剖面的对话框,允许您设置视线分析或优化端点。

智慧空间实验室 2049

你不知道这份超详细JVM内存结构?极其重要

前言 高并发十分考验架构师功底,它也是分布式架构设计中必须考虑的因素之一。要知道,光靠服务器堆是没有出路的。 想看看大牛是怎么面对高并发的?想知道BATJ大厂是怎么设计高可用架构的?这里有可参考的实践案例,干货满满,或许能对你有所启发。 Redis常用的数据类型 Redis的五种常用的数据类型分别是:String、Hash、List、Set和Sorted set Redis的使用场景 1.Counting(计数) 2.展示最近、最热、点击率最高、活跃度最高等等条件的top list 3.用户最近访问记录也

m0_56662340的博客 156

vue2/3 - 【超详细】最新网站接入使用支付宝支付功能,点击支付跳转新页面后生成订单及支付二维码,实现支付宝在线付款详细的教程(整个支付的完整配置及支付流程,一键复制源码开箱即用)!

vue支付宝付款,vue支付宝支付,vue如何实现支付宝在线付款,vue网页pc项目接入支付宝支付,vue支付宝支付详细教程,vue2支付宝在线支付的详细示例代码,vue如何做支付宝付款,vue怎么实现支付宝的付款功能,vue调用支付宝进行付款支付,vue PC项目实现 支付宝支付,vue h5页面调用支付宝支付,vue页面唤起支付宝支付功能,vue支付宝支付跳转到新页面,vue如何跳转新开一页展示支付宝二维码支付,vue怎么新开页面进行支付宝在线支付,vue新页面支付宝支付功能,前端vue支付宝支付教程,

✅ 精选推荐文章 5729

大中型超市收银系统(可直接运行)

光步前台收银系统系统功能:商品销售、商品退货、挂单、收银员权限、会员销售、单品取消、整单取消、商品查询、脱机销售、脱机数据上传,基本资料下载,开钱箱、小票打印、收款结算,支持多币种付款方式(现金、储值卡、礼券、微信等),支持多种促销。运行环境:.net 4.0登陆信息用户名:1001 密码:123456内置商品信息,商品编码可输入00001000 - 00010000,测试效果相关功能键F5 结算 F9挂单 F11商品查询 F8退货 Insert单品取消 Del整单取消 F12开钱箱F2 会员 Ctrl+Z退出系统 Home 锁屏 相关源码待公开

技术分享链接汇总[201805]

内容整理自-&amp;amp;amp;amp;amp;gt;java高级交流群【329019348】更多Java高级交流文章 2018/05/02 It互联网项目经理,如何书写出色的技术文档? 基于Go构建滴滴核心业务平台的实践 现代IM系统中聊天消息的同步和存储方案探讨 微信红包的架构设计简介 Circuit Breaker: Hystrix Clients Java SE 7新特性:改进使用带泛型可变参数的方法时的...

六月星空2011的博客 474

文档:亲测可用解决vnc灰屏,黑屏,鼠标大黑叉情况

主要解决vnc-viewer灰屏,黑屏,鼠标大黑叉等现象,详细见文档。

纯干货丨18个软件开发常见问题及解决策略,你有遇到吗?

本文转载自:纯干货丨18个软件开发常见问题及解决策略,你有遇到吗? No.1 每次看这些架构的思想方法的时候,总是和实际的应用没能很好的结合起来,原因是不是架构设计的实践不够?或者是对各种实现的分析和思考太少? 我觉得不仅要有架构实践,还要有不同场景的实践。 举个例子来说,你平时做企业应用架构,没什么流量,没多少数据,复杂的地方都在业务逻辑,这时候你去看那些讲大数据、讲高并发的文章,很难带入到场景去。 还有就是一些架构,不自己搭一遍是很难了解其中的优缺点的,这也是另一个原因。 可以考虑有机会自己尝试,把看

Java_Cappuccino的博客 4997

WINCC7.3破解文件

WINCC7.3硬件够破解文件,有需要的下载!WINCC7.3硬件够破解文件,有需要的下载!

android 蓝牙通讯demo

android 下蓝牙通讯demo,实现了发现蓝牙,使能蓝牙,通过蓝牙发送消息。

阿里架构师分享丨Java架构设计的重点知识和学习路径(建议收藏)

本文已收录GitHub,更有互联网大厂面试真题,面试攻略,高效学习资料等 学习架构呢,要掌握的东西有很多,你是不是开始担心自己一辈子都学不完呢?其实,我们也不需要一下子铺开学习所有的架构技能,重要的是把控好学习的节奏,在适当的时间学习适当的内容,我们可以结合实际工作,一步步地成长。所以今天这一讲,我想给你提供一些架构学习的重点方向和路径建议。 架构原则汇总 在技术架构篇,我针对系统的高可用、高性能、可伸缩和低成本,给你介绍了很多的架构设计原则,不同的原则对应着不同的目标,这里我把这些架构原则和目标汇总成.

Java_Cappuccino的博客 2202

迟来的四月java面经分享,七面收割五个offer,大厂也不过如此!

都说金三银四是找工作的最佳时节,由于本人的个人职业规划跟目前工作内容不太相符(具体原因就不透露了,领导平时也要来这里逛,哈哈),四月份挑选了10多家公司投递简历(公司规模从几十人到上万人都有),参加了7家公司的电话面试,收获了5个offer,也还算不错。下面就分享一下面试过程中一些基础的,又最常见的问题。不啰嗦了,直接看题。 1. synchronized你用过吗?synchronized和Loc...

Java_Cappuccino的博客 2045

java开发者必知必会的50个Redis知识点,面试/学习都无所畏惧

Redis作为目前的主流NoSql数据库,不会是不可能的,在面试中也是非常高频的,一定不能在这个环节丢分,不管是学习,还是面试,以下知识点,都有必要掌握。 1.Redis是什么? Redis是一个开放源代码(BSD许可)的内存中数据结构存储,可用作数据库,缓存和消息代理,是一个基于键值对的NoSQl数据库。 2.Redis特性? 速度快 基于键值对的数据结构服务器 丰富的功能、丰富的数据结构 简单稳定 客户端语言多 持久化 主从复制 高可以 & 分布式 3.Redis合适的应用场景? 缓存 排

Java_Cappuccino的博客 1204

程序员职场小技巧:每天工作那么多事,如何安排事务的优先级?

最新互联网大厂面试真题、Java程序员面试策略(面试前的准备、面试中的技巧)请移步GitHub 我们在日常工作中,总会这样感慨:事情,是干不完的。既然干不完,那我们就要分清轻重缓急,哪个重要,哪个不重要,给它们划分一个优先级,这样不至于让自己手忙脚乱。 能给手头的事情排上正确的优先级,是一项很重要的工作能力。 当然,我们在生活和学习中,事情也可能不少。但是和工作中的优先级相比,生活和学习里的事情是我们自己的事情,只要安排得让我们自己满意就可以了。在工作中,事情的优先级的标准,是要让公司受益,让老板满意,让

Java_Cappuccino的博客 1161

还搞不清楚JVM是怎么处理异常的?这水平,跳槽都没人要

本文已收录GitHub,更有互联网大厂面试真题,面试攻略,高效学习资料等 文章目录异常的基本概念Java虚拟机是如何捕获异常的?Java 7的Supressed异常以及语法糖总结与实践 众所周知,异常处理的两大组成要素是抛出异常和捕获异常。这两大要素共同实现程序控制流的非正常转移。 抛出异常可分为显式和隐式两种。显式抛异常的主体是应用程序,它指的是在程序中使用“throw”关键字,手动将异常实例抛出。 隐式抛异常的主体则是 Java 虚拟机,它指的是 Java 虚拟机在执行过程中,碰到无法继续执行的异常.

Java_Cappuccino的博客 1049

不用怀疑!这就是把Java.I/O流讲解的最清楚的一篇文章

最新互联网大厂面试真题、Java程序员面试策略(面试前的准备、面试中的技巧)请访问GitHub 文章目录简单梳理理解File类简单梳理File操作递归遍历文件文件流:数据流的读写都是基于文件的操作FileInputStream:字节输入流FileOutputStream:字节输出流复制文件到指定位置FileReader:字符输入流FileWriter:字符输出流复制文件到指定位置(字符流只适合操作内容是字符文件)缓冲流:数据流的读写都是基于内存的操作BufferedInputStream:缓冲字节输入流Bu

Java_Cappuccino的博客 947

详解Linux系统安全:多人共用服务器,如何防止别人干“坏事”?

本文已收录GitHub,更有互联网大厂面试真题,面试攻略,高效学习资料等 本文就讨论一下 Linux 系统和应用安全。我们知道,在开发一个应用的过程中,需要涉及代码、操作系统、网络和数据库等多个方面。所以,只是了解代码安全肯定是不够的,我们还需要了解常见的基础环境和工具中的安全机制,学会通过正确地配置这些安全机制,来提升安全保障。 谈到 Linux,我相信你每天都在使用 Linux 进行各种开发和运维操作。但是,大多数情况下,公司不会给每一个员工分配专有的 Linux 服务器,而是多个开发和运维共用一台.

Java_Cappuccino的博客 928
上一篇: 先打好基础,阿里架构师一文带你深入理解JVM内存回收机制
下一篇: 在面试了阿里、腾讯众多大厂之后,我终明白了为什么需要消息队列
Java_Cappuccino
博客等级 码龄7年 17粉丝 64原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值