粉丝9694获赞3.3万

我们来看一下加微号母这个环境变量的配置,加微号母这个环境变量比较特殊,你不配置他呢?你的编译和运行呢,都是可以进行的,我们来看一下加微号母需要配置什么样的参数。我们首先我们看到这个图呢,有两个部分,一个部分呢是其他应用啊,一个部分呢是家务取引机, 我们在这个应用上呢,我们可以看到,哎,这里有相应的什么 tombat 啊, akineps 啊,这些相应的一些程序,或者是一些开发工具。 那这些开发工具为什么会用到加瓦浩姆这个环境面料呢?是这样子的,因为加瓦浩姆这个环境面料它指向的是 jdk 的安装目录,或者是这个加 e 的这个安装目录啊,当我们这些程序在启动的时候呢,它会自动去搜索这个目录下面的其他的一些资源文件, 其实也是告诉他,哎,这个 gdk 啊或者嘉义呢安装在哪里啊?他好去寻找,因为真正他们启动的时候呢,他其实也是不会依赖 碍于这个家伙项目的,而是会去依赖一个 pass 的这个环境面料。来我们来看一下吧系统上的一个配置啊,这个就是咱们的家伙项目指向的这个 gdk 的,按照目录,我们来看一下这个 gdk 目录下的内容, 看,这就是 gdk 下面的一些情况,他这里面呢还有一个叫 gr e 的,其实你把这个路径配置到这下面也可以,因为 g r e 呢是家伙的运行环境 啊,如果我们不做编译的话,只做运行的话,那我只带着这个加意就可以了,如果我要做编译的话,那我肯定是要用开发工具包才可以, 所以呢,在这个配置的时候呢,就看你的需求是什么,如果你的需求说啊,我仅仅只是把这个程序运行起来,那我其实只带着这个加意走就可以了啊,如果我说我要开发又要运行,那我就把这个 gdk 安装好就行了。所以在这个配置的时候,这个加个号码呢,也 不一定说我非得要指向叫在这个 gdk 下面,也可以指向到这个加意下面来,我们简单总结一下,加完号我不一定要配置 啊,因为在我们初学加瓦的时候呢,其实很少能用得到加号码啊,但是其他的应用程序在启动的时候呢,就加瓦的应用程序在启动的时候,他可能就需要去找这个加号码,所以呢,这个加号码呢,我们在后期的一些服务器程序啊, ada 啊这些相应的工具上呢,可能是需要配置的。第二点, 加油号,我配置虚拟机的安装目录吗?啊,其实呢,这个我们刚刚也说过了,我说哎,你可以配置到吉利可以目录下,也可以配置到加意目录下啊,这都是可以的,就看你的需求是什么。 如果说我仅仅只是运行一个程序啊,那我就配置一个加 e 就行了啊,如果我是编译加运行,也就是在我们学习期的这种开发环境中,那我就需要配置 gdk, 因为 gdk 和加 e 是有一些区别的啊,所以在后期的视频上我可以讲解一下。

大家好,今天教大家怎么安装 java, 首先依旧是在浏览器搜索 java, 然后点击这个 java downloads, 有 两个 lts 长期支持版,就是 jdk 二十五和二十一, 如果大家还想下载其他版本的的话,可以点击 java akf, 这里有 java se 等等其他的旧版本, 那我们就选择一个 jdk 二一下载,选择 windows, 点击这个 x 六四 installer, 更改一下安装位置, 然后按下微按,搜索系统环境变量 这边新建一个名为 java home 的 变量, 找到刚刚安装 java 的 位置, 变量值设为这个, 然后在 pad 变量中再新建一个 java, 后面跟上闭幕录, 点击确定, 打开 cmd, 输入 java version, 再输入 java version, 看到都是二十一零九。 然后呢,在文件资源管理器中点击查看,勾选这个文件扩展名。 之后呢,可以在桌面新建一个文档, 后置改为 java, 输入这个 hello world java 代码,保存一下 文件名。那要改为 hello world, 打开 cmd 啊, cd 到桌面目录下, 输入 java x hello world java, 再输入 java hello world java, ok, 可以 一键成功打印了这个 hello world。 好 了,那本次的 java 安装教程就到此结束了,我是炳坤,我们下期再见。

大家好,我今天来录制一下这个,那一般的 springboard java 的 成品项目,它的一个结构目录以及各个地方是干什么的,是整个的一个讲解啊。那么首先我们,呃进入它整个的 这个项目啊,我们能够看到它是由这几部分构成的,点 i d e a, 这个不用管,这个是创建 i d e a 的 时候,是 i d e a 创建这个项目的时候就会有的啊,这个不用管 s r c 项目,那么它 是我们的元代码部分啊,它把 java 也放这这里面来了,另外它把 v o e 也放到这里面来了。一会话我们会详细的说, 啊,啊?还是这个 power 文件, power 文件啊,那么对于 java 来说,它是没问下面的啊,它是告诉你啊,有什么依赖以及依赖的版本啊,以及依赖的版本啊,比如说这个这样 就是认证用的啊,以及它的一个版本。那么相对于其他正常的项目啊, 这种成品项目最大的问题是会出现很多你没有必要的项目会出现在这里面。呃,这已经经过筛检了,这个已经是经过筛检了啊,比如说这一个,那么它已经有 sql server, 那 么它还有会有马斯克, 因为它不只是给你一个人提供嘛,所以说啊,它会把一个相当于公约数这样的,把各个地方都会放进来,百度智能之类的,这一个是还有一个 redmi, 呃,这个我们主要看 s s r c 下面, s r c 下面啊,这个 test 里面啊,只是以少部分的 测试,这个是不用管的,我们主要看 mate 里面啊,又包括 java 和 resource, resource 下面呢是一些资源,还有一些静态文件,这个我们等会来讲,我们先看 java 里面, java 里面是大家比较熟悉的 java 的 这一套结构逻辑, 那么对于 spring boot 来说,这个 spring boot 点击是可以运行的。上,从上到下我们依次来看一下,嗯, on intention, no attention, 它是自定义注解,自定义注解的话,我们一般啊主要是看这个就行了,就看这个,其他的话可能用不到, 这是对于忽略,那么他的含义啊是,呃,你不需要登录啊,我用了它之后不需要登录,你就可以访问这个接口,那么他具体是怎么实现啊?我们一会介绍到。呃,介绍到这个拦截器这一部分,我们再具体去讲讲解哈。 讲解,你知道它是一个自定义注解就行了。这个包下面,呃,另外这个是 configure, configure 下面它是,呃 spring boot 下面的一个配置类,呃,在这个地方啊,它是配置了,呃,连接器和连接器,其实是包含 spring, 嗯嗯, spring, 呃, m m v c 这种 web 端的这种,呃设置,它主要啊是拦截和放行啊,拦截和放行一些,放行一些精彩文件啊。 my mate plus 里面主要是,呃启动它的一个 呃,分页啊,请多来一个分页,因为他是比较老的版本啊,这个是大家比较熟悉的 ctrl 的, 我们可以叫他控制层,也可以叫他接口层,他的话是我们对外呃提供服务的这么一个最前端的这么一个接口啊,那么你在 页面中请求 url 是 到这个 controller 层, controller 层啊,它下面会调用 service, 是 这个 service。 哦,我们来讲一下 service 层, service 的 话,它是一个呈象棋下的, 它的主要的功能是去继承这个 m, 嗯,是 maptisplus, 它里面的这些功能是在 maptisplus 实现不了的时候,它就会自定义一些方法,它自定义一些方法是依据下层去实现的啊,依据下层去实现的, 那么这个地方是接口层,那么它就会有对应的实线层,这里面是实线层,对应的它在后面会有一个 r、 m、 p、 l 作为后缀。对, 这里面它是接口,接口它是只有声明,而这里面它是包含实线的啊,就包含实线入参、执行方法以及返回。 呃,都大同小异,基本上都会去调用这个 base map 啊,这一个,这个 base map, 它的这个啊 map base plus, 这里面自带的它下一层啊,其实还是调用这个道儿层,调用这个道儿,那么它调用这个道儿, 我们在 map base plus 里面,这个应该也可以叫做 map 层。 map, 呃,它 在 java 层里面也是去写接口,不用写实线。去写实线,那么它的实线其实是在 results 下面的 map 里面对应着有插面文件, 插面文件里面的 i 法就跟它的 do 层里面的这个方法名是对应起来的,是对于一个指引,这个是 mybites 去设计的,去设计的半自动化的形式。好,我们再继续。我们讲完了 control 以及 service, 那 么这三部分递进的一个关系。 这个 dos 啊,你也可以认为它是 map 层,那么剩下是一个 entry, 这个 entry 啊,它分为好几个,这个好几个啊,我们不用太担心,那么我们依次来介绍。首先这种 entry 啊,它是跟你的数据库去绑定的,它会有一个呢 tab, 呃, tab 名, 他们那把是跟你的数据库强相关的,尤其是这种项目,一般都是中文的这个拼音,也没有联字符,这个要注意一下就行了。其实在实际的工作当中啊,这种东西也比较常见,比较常见, 那么其他的第一部分是 model, 那 么这些的用处是什么呢?是 vivo 啊, vivo 字里面有可能是有 table 的,是也是有对应的关系的,但是它的话一般都会有继承关系,一般会有继承关系是你当你去返回一个值,当你去返回,你不会把所有的数据都想返回给它 吗?不会都去返回给它,那么就用这种 vivo 的 形式去查询一部分数据的这个用户,而不是全部的 vivo 的, 还有可能还有可能是拼接,那么你在数据库里面查询的话,是两个表或多个表,你返回数据,你去返回一个 vol, 那 么 vol 里面是包含着三个表里面的需要的数据,这样的一个关系。 model 里面啊,有,你在数据库里面啊,可能会用到的, 在他这个,他这个都没有用到,他标灰了就没有用到,是有一大堆的溶液,是不是给你用的,相对的你有一些东西啊,也可能不是别人用的。那好,这个连接器这一块我们再讲解一下,然后顺带把前面的一个问啊给说一下。是,这不是忽略吗? 他的忽略是怎么用的呢?两部分,第一部分啊,是在第一部分是在 control 里面,那么在这里面设置一下, 这里面去设置一下,设置它不会起作用,注解的作用啊,你如果想实现它,你又得用它,你如果是直接写上去,你是弄不了的,你需要实现它,怎么实现呢? 那么就在这一个拦截器里面去了,它拦截器里面啊,它会啊,第五十一行会去说明一下是如果这个方法有这个,有这个忽略的这个 class, 那么那么我我就会直接放行,就会直接放行,就会忽略吗?那么下下一步是这个 优秀,优秀,两边下也是重灾区啊,你会发现他很多用不到的东西都会放到这个里面,用到的东西这边是不会是实体的,而不是那种灰色的,有一下他是灰色的,那说明他是用到了,用到了,用到了,但是不一定是怎么用的,这有没有用到 侧壳就用到了,而这是防侧壳注入的,这一般还还有工具,工具叫燕的啊。 java 代码这一块,这就讲解完了,那我们再看一下它里面会前端啊,一般来说都是 v o e 的 这两个 v o e 它是有一个,有一个前端和一个后端,我们这里面说的前端后端其实都是外部端,那么我们可以理解为一个是展示端,比如说一个商城吧, 商城啊,他要在前端给用户用的,我们就叫前端。还有一块是管理端,我们也可以叫做后端,是 adm 或者什么去处理。你前端展示用户看到那些商品都是由后端去去创建,去生成,去修改订单也都是从前端到后端这样的一个过程, 那么它就有一个 front 和一个匿名,就是一个前端,一个后端。但是啊,它给你的这个项目里面是 v u e, 没错,会给你一个 d s t d i s t 文件,这个文件呢,这个文件夹 v u e 编辑之后去生成的这个代码,这个代码是不可读的,这个代码是不可读的,也不可修改,如果你用强替换是可以的,但是你如果是想去修改 v u e 原码, 它是不生效的啊,它是不生效的。整个的 java 项目啊,它最后会读是 dst 里面的文件,如果你想去修改,你就得 把 node js 的 环境配上去修改代码,然后运行这个 build, 或者是你直接运行 npm run build, 就 可以去 重置覆盖这个 dsit 文件。它是用的很老的 node 版本,有可能都是十十四的, 这四十六的就非常痛苦,改起来非常痛苦,尤其是这个玩意是 note size, 装它很痛苦的,装它很痛苦都不建议了,尤其是有 ai 的 情况下,如果你能将就用,那就将就用是最好的。如果你将就用不了,我建议你重新从头写着。 那么前端和后端 v o e 块还有这一块 static static 啊,它因为它会放到这个 s r c 下面嘛? s r c 下面,那么它运行之后, java 会把它放到这个 tag 文件里面, tag 文件夹里面啊,那么你 重新重新运行或者什么它上传文件啊,就会有一个,有一个只存储到这个文件夹里面,所以说你上传了,但是发现变化 没有?变化啊,你重启以后他又有了,是这个问题导致的。那么解决他的问题方法也很简单,就是把他的 tab 文件,是把他的这个呃上传目录放到这个外面就可以了,就能解决了,这个我是解决过的。嗯, 那么最后一个文件,我们看这个文件配置文件是整体的 spring boot 里面的配置文件啊,他会有相当多的配置,那么基本上我们只需要去更改这个数据库的用户名密码就行了,其他的话,呃,没有必要去改他。嗯,其他话是没有必要去改他就是这种成品。 好,那今天的话是去讲解这个 java spring boot 成品项目啊,就这样,如果有问的话可以评论区发一下。

大家好,今天我们来学习 java 中非常重要的两个概念,封装与访问控制。封装是面向对象三大特性之一,它能让你的代码更安全,更容易维护。 访问控制通过 private、 public 等关键字实现,它们决定了谁可以访问类的成员。 学完这节课,你将能够设计出符合 java bin 规范的类,并避免很多新手常犯的安全错误。 我会结合实际工作场景演示封装如何保护数据,并给出常见问题的排查方法。最后记得多动手敲代码。 先看一个没有封装的例子,我们定义 student name 和 h, 没有加任何修饰符,默认是包即可见。在外部,我们可以直接通过点号访问 h 属性,甚至把它复制为复数。这显然不符合现实逻辑, 如果程序里到处都能直接修改对象,内部数据一旦出现错误,排查会非常困难。 封装的核心思想就是将属性隐藏起来,对外提供受控的访问方法,就像药品封装在胶囊里。接下来我们学习如何用访问修饰符实现封装。 java 提供了四种访问修饰符控制成员变量和方法的可见范围。最严格的是 private, 被它修饰的成员只能在本类内部访问,外部完全看不见。 如果不写任何修饰符,就是 default, 也叫包级私有。同一个包下的类可以访问 protected 比 default 多了一个权限,子类可以访问,哪怕子类在不同包, 最宽松的是 public, 任何地方的代码都能访问。实际开发中,我们通常用 private 加 public 方法实现封装。标准的封装做法,用 private 修饰属性,然后提供 public 的 getter 和 setter 方法。 getter 用于获取属性值,命名规则是 get 家属姓名首字母大写,返回类型与属性一致。 setter 用于修改属性值,命名规则是 set 家属姓名首字母大写,参数类型与属性一致,一般没有返回值。 这样外部就不能直接访问 name 和 age 了,必须通过方法。如果以后需要改变内部存储方式,只需修改 geter setter 即可。很多框架如 spring my betas 也依赖这种命名规范来操作属性。 实际工作中,我们经常在 setter 里加入参数校验,防止无效数据进入对象。 比如年龄应该在零到一百五十之间,如果传入负数或过大数值,就抛出 illegal argument exception。 异常 姓名不能为 now, 也不能是空字浮串,用 trim 检查是否全是空白字母。这种防御性编程能极大提高程序的健壮性。错误在复制阶段就被发现了。 注意,异常信息要清晰,方便调用者知道哪里出错了。这是企业级代码的常见实践。构造方法负责在创建对象时初使化属性。为了保持较验逻辑统一,我们可以在构造方法中调用 setter。 这样无论是通过构造方法还是后续的 set 修改,都会执行相同的校验规则。如果类需要支持无参构造,比如某些框架要求就显示写出无参构造方法。 注意,一旦你写了有参构造,默认的无参构造就不再自动提供,需要手动添加。 好的封装习惯是所有对私有属性的写入都经过 set, 哪怕是构造方法内部。 我们来看一个实际工作场景,银行账户类 balance 是 私有属性,外部不能直接修改。提供 deposit 存款方法,金额必须为正数,否则抛出异常,然后增加余额。 提供 withdrawal 取款方法同样需要正数,而且不能超过当前余额,否则提示余额不足。 get balance 方法只读,没有 settle, 因为余额只能通过存取款改变,不能随意设置。 这种设计符合真实业务规则。封装保证了账户金额的完整性,这就是封装的力量。 新手最容易犯的错误,试图直接访问 private 属性,编辑器汇报 name has private access。 解决方法是改用 setter 方法,记住外部永远不能直接点出私有字段。 另一个常见错误, geter setter 命名不规范,比如 setage 写成 setage 首字母没大写 jabao bin。 规范要求方法名是 set 后跟属性名首字母大写,否则很多框架无法识别。排查技巧,仔细检查方法名拼写,或者用 id 自动生成 geter setter, 避免手写错误。 另一个常见异常是 no pointer exception, 你 声明了 person 变量,但忘记 new, 直接调用 setter 就 会报错。解决方法,确保用 new 创建对象,或者从工厂方法获取非空对象。 还有参数名与成员变量同名时,如果不加 this, 会造成自己赋值给自己的问题。 正确写法是 this 点 name 等于 name, 用 this 区分成员变量和局部变量。我建议你们每次写 center 时都用 this 前缀,养成好习惯,能避免大量低级错误。 今天我们学习了封装与访问控制。封装的三要素,属性私有化提供公共方法,在方法中加入较验逻辑, 访问修饰符 private default protected public 的 可见范围要牢记,实际工作中,几乎所有的 java 类都会遵循 java bin 规范,即私有属性加 geter setter。 我 给你的建议是,自己动手创建一个 product 类,包含 id name price, 实现封装和校验。 光看视频是学不会编程的,一定要打开 i d e 亲手敲一遍代码,遇到错误自己排查。建议收藏本视频,反复练习。

二零二六年了,还在为 java 基础语法发愁吗?今天这节没有花里胡哨的特效,全是干货。标识符、关键字、数据类型、变量、常量、运算符、类型转换、输入输出统统讲透。 而且每讲一个知识点,我立刻就切到代码,你能看到代码怎么敲,怎么翻译,怎么运行。遇到报错,我们当场排查解决。不装高手, 我还会把踩了十年的坑一次性分享给你。视频末尾你会写出第一个交互式程序, 建议现在点收藏,以后写代码会经常回来查,准备好你的 idea 或 vs code, 马上发车。标识符就是你给类方法变量起的名字,规则很简单,字母、数字、下划线、美元符号组成, 绝对不能。数字开头也不能用关键字,特别注意 true, false, no 是 字面量,它们同样不能当标识服用,很多新手栽在这里。关键字一共有五十多个,比如 class, public, 这些单词在 java 里有特殊含义,不能占为己有。 student name 比 s 要好维护得多, 光说不练假把式,我们去 vs code 里验证一下。现在我们写一个类来测试合法的标识符。注意,我起的变量名都是符合规则的,如果你把变量名改成数字开头或者关键字,翻译器会直接报红字提醒你 整数。四种 bite short, int, long 赋点两种 float 和精度更高的 double 字母就是叉儿不尔值,只有 true 和 false。 记住它们占用的字节数和取值范围。 byte 一个字节 short, 两个 int, 四个 long, 八个字节赋值时记得加 l 后缀。 float 赋值要加 f 后缀,否则默认是 double。 实际开发中 int 和 double 用得最多, 除非内存特别紧张才会考虑 byte 或 short。 现在我们写个类,把八种类型都声明一遍。这个类里我声明了所有基本数据类型。 注意 long 数字后面的大写 l, 还有 float 数字后面的小写 f。 翻译运行一下看看控制台输出 变量就是一个可以存放数据的容器。声明变量就是告诉翻译器要多大,内存格式是数据类型加变量名分号结尾始化就是第一次给变量赋值, 也可以声明的同时就始化,一步到位。 java 要求局部变量使用前必须始化, 否则编辑器会报错,这是安全机制。如果变量值不想被修改,就用 final 修饰。 final 修饰的变量叫长量,只能复制一次。长量命名一般全部大写单词用下划线隔开, 比如 max 下划线 value, 一 看就知道是长量。下面我们写代码演示变量和长量的区别。 我声明了一个 int 变量 h 并赋值,又声明并出示化了字母串 name 还有 final 常量 pi, 尝试修改它就会报错。运行一下看看控制台输出结果。 运算符是告诉计算机执行什么操作的符号。算数运算符就是加减乘除和取余数,整数相处,结果还是整数,小数部分直接砍掉关系。运算符用来比较大小,结果是不尔值。 注意等于号是两个等号,一个等号是负值。逻辑运算符处理不尔值与或非运算短路效应是面试高频考点。 如果左边已经能决定结果,右边就不算了,自增自减分。前缀和后缀效果不一样,前缀是先加后用,后缀是先用后加。我们马上写个累,把这些运算符都测一遍。 这个类掩饰了算术关系逻辑和自增熵算符。重点看整数除法和取余的结果,还有自增前缀和后缀的区别。翻译运行,观察控制台每一行的输出 类型。转换是让不同数据类型一起参与熵算。小范围转大范围是自动的,很安全。比如 int 赋值给 int, 但是大范围转小范围必须强制转换。强制转换的语法是括号里写目标类型, 比如浪转 int 要写成括号 int。 强制转换有风险,可能丢失精度或溢出, 实际开发中要小心。 int 转 byte 超过一百二十七就会变成负数,很坑。字串和基本类型转换要用包装类方法,比如 integer 点 parseint 字串。我们写个例子看看转换会发生什么。 这里演示了自动转换和强制转换。注意 double 转 int 会直接砍掉小数 int 一 百三转 byte 变成了负一百二十六。运行一下,看看控制台输出,理解易出现象, 程序不能只输出,还得能接收用户输入。 java 用 scanner 类实现键盘输入。第一步,导入 java 点 u t i 要点 scanner。 第二步,创建 scanner, 对 象参数是 system in, 然后就可以用对象点方法读取数据了。 next line 读一行字符串, next int 读整数, next double 读小数,非常直观。注意会用 next line 和其他方法时有坑,因为回车符残留会导致 next line 直接跳过。解决办法是额外多写一句 next line 是 调换行, 最后养成好习惯,用 close 方法释放资源。我们马上写一个可以和用户对话的程序, 这个程序会问你的名字、年龄和身高。运行后在控制台输入对应信息,注意输入身高时用英文句点而不是逗号。试试看,你已经能写出交互程序了, 恭喜你坚持到了最后,非常了不起。这一节我们把 java 基础语法全过了一遍,而且不是纸上谈兵,每个点都写了代码, 你最好把演示代码自己敲三遍以上。光看视频是学不会编程的,一定要动手把代码里故意埋的错误也自己重现一遍。 比如 int 一 百三转, byte 一 出,比如变量未初始化就使用汇报错,只有亲手遇到问题再解决,记忆才深刻。下节课我们讲流程控制、 if else 和循环, 到时程序就能做判断和重复执行了。感谢你认真看完这节干货满满的视频,如果觉得有用,记得收藏,方便以后复习,我们下节课再见!

欢迎来到 java 编程入门到精通系列课程,今天我们来攻克第三阶段流程控制语句。流程控制是程序的灵魂所在,没有它,代码就只能从上到下限性执行。今天你将彻底掌握 f l s 分 支,选择 switch 多路开关语句 for well 和 do well 三种循环结构,还有 break, continue 和 return 控制转移, 每个语法点都会立刻进入实战演示,拒绝纸上谈兵,只讲干货,全程高能,建议你收藏起来反复观看。准备好了吗?让我们马上开始 java 程序的执行顺序默认是从上到下,这种结构我们称为顺序结构,比如这里声明变量 a 等于十, 然后声明 b 等于二十,接着计算 a 加 b 赋值给 sum, 最后打印输出结果。 每一步都是按书写顺序执行,但如果只有顺序结构,程序会很死板, 我们需要根据条件改变执行路径,这就是流程控制语句的价值。我们打开 vs code, 编辑一个顺序结构的事例,定义类 sequential demo 和 main 方法,声明两个变量 a 和 b, 并计算它们的和 现在,翻译并运行它,看看输出结果。这就是最基础的顺序执行流程。 if 语句是最基础的条件判断结构,格式是 if 后面跟小括号里的不尔表达式, 如果表达式为真,就执行大括号里的代码,否则直接跳过不执行。势利中 score 等于八十五,判断 score 大 于等于六十,乘以 于是输出及格两个字。注意,即使大括号里只有一条语句,也建议始终使用大括号,避免歧义。这是一种防御性编程的实践。现在创建 if single demo 类来演示 if 单分支, 设定一个分数变量, score 为八十五,用 if 判断是否大于等于六十,条件成立则输出及格。最后无论条件是否成立,都会输出判断结束。翻译运行可以看到只输出了及格。 if else 可以 实现二选一的逻辑,如果条件成立,执行 if 代码快,否则执行 else 代码快。 这里 store 等于五十五,不满足大于等于六十,所以跳转到 else 部分输出不及格。 if else 语句在实际工作中非常常用,比如根据用户登录状态显示不同页面, 根据订单金额决定是否包邮等等。我们创建 ifls demo 类来演示双分之,把分数改成五十五分,用 ifls 判断及格与否,这次会输出不及格。翻译运行验证一下结果。 当有多个条件判断时,使用 else if 结构,它会从上到下依次检查每个条件,一旦某个条件成立,就执行对应代码, 并且跳过后续的所有判断。这里 score 为八十五,先检查是否大于等于九十不成立, 再检查是否大于等于八十成立,于是输出良好,后续的及格判断就不会再执行了。注意,条件的顺序很重要,把最严格的条件放在最前面,否则会导致逻辑错误。 创建 multi f demo 类演示多分之等级判断,定义分数为八十五,用 else f 链条判断等级输出良好。编辑运行看到正确结果。你可以尝试修改 score 值,观察不同输出。 switch 语句用于处理多路分支选择,它支持整数符串和每举类型。这里定义 day 等于三。 switch 匹配到 case 三输出星期三,每个 case 后通常要加 break, 否则会发生穿透。继续执行下一个 case。 default 分 支用于处理未匹配的情况。在 java 十四以后, switch 还支持箭头语法,可以让代码更加简洁易读。 我们会在新特性部分详细讲解。创建 switch demo 类演示星期转换定义变量, day 为三,使用 switch case 匹配星期几编辑运行输出星期三, 你可以试着去掉 break, 观察穿透效果,但要小心,这通常会导致 bug。 for 循环是最常用的循环结构,它由三部分组成,出使化条件更新, 首先执行 int i 等于零出使化一次,然后判断小于五是否成立, 成立则执行循环题,打印 i 的 值,执行完后执行 i 加加,更新循环变量,再次判断条件,直到条件为假,结束。负二循环特别适合次数确定的场景,比如便利数组或集合。 创建 for loop demo 演示基本 for 循环,循环变量 i 从零到四共执行五次,每次打印 i 的 当前值。翻译运行可以看到零到四的输出,这是最经典的循环结构。 y o 循环,在每次迭代前检查条件,如果条件为真就执行循环体,这里 count 出示为零,判断 count 小 于五成立,进入循环,打印 count 值并自增, 一直到 count 等于五时,条件不成立,退出。 y o 适用于循环次数不定的场景, 比如读取文件直到末尾。要注意在循环体内改变循环变量,否则可能导致死循环。创建 while loop demo 类演示 while 循环定义 count 出示为零,只要 count 小 于五就打印并自增。 翻译运行可以看到零到四的输出。注意,如果忘记 count, 加加就会无限循环。 do while 循环和 while 的 唯一区别是,它至少会执行一次循环体,因为条件检查放在循环末尾。这里 number 出使为五, 先执行 do 快 打印 number 等于五,然后 number 自增为六,再判断 while 条件 number 小 于五,不成立。 循环结束,但至少执行了一次。这在需要先执行再判断的场景很有用,比如显示菜单后获取用户选择。 创建 do well demo 类演示至少执行一次 number 出示为五。 do 快 里打印 number 的 值并自增,然后判断 number 小 于五为假,退出翻译运行。可以看到只打印了一次, number 等于五, 这就是先执行后判断的效果。 break 语句用于立即终止当前循环。这里 for 循环本应从零执行到九, 但当 i 等于五十,执行 break, 循环立即结束,不再执行后续迭代,所以最终只会打印零到四。 break 也可以用于跳出 switch 语句,在实际开发中常用来提前结束搜索,比如在数组中找到了目标元素 就可以 break 终止,后续无用便利。创建 break demo 类演示 break 提前终止循环变量 i 从零到九,当 i 等于五十,执行 break 跳出,所以只打印了零到四。编一运行验证一下输出结果。 break 会让程序跳转到循环后的下一条语句。 continue 语句跳过本次循环的剩余部分,直接进入下一次迭代 这里当 i 等于二十,执行 continue。 本次循环的打印语句被跳过,直接进行 i 加加开始下一轮,所以输出为零一三四。 continue 常用于过滤某些特定情况,比如只处理偶数,跳过基数, 或者跳过某些无效的数据项。创建 continue demo 演示跳过效果,当 i 等于二时,执行 continue, 导致二没有被打印。翻译运行可以看到零一三四的输出。 continue 让循环继续,而不是终止。 return 语句用于从方法中返回结果,同时立即结束方法的执行。这里定义一个 add 方法,接收两个整数,返回它们的和。 如果方法返回类型为 void, 可以 使用不带值的 return 提前退出。 return 也是一种控制流程的手段, 尤其在递归和提前返回时非常关键。创建 return demo 类,演示 return, 用法定义静态方法 add 返回两数之合。在 main 方法中调用 add 并打印结果。翻译运行可以看到输出三加五等于八。 return 将计算后的值返回给调用者。 现在我们综合运用所学,写一个猜数字游戏 程序,随机生成一个一到一百的整数。用户输入猜测的数字程序,提示大了小了或猜对。这里用到了 do well 循环,因为至少要猜一次。用 if else if 给出大小提示, 猜对后循环结束输出。恭喜!这个案例非常经典,是很多编程新手必做的小项目。创建 guess number 类,开始综合实战。用 math random 生成目标数字。 用 scanner 接收用户输入 do while 循环,确保至少猜一次 if else 判断大小并给出提示,猜对后循环结束输出。恭喜!现在翻译运行试试猜数字游戏吧, 你可以尝试输入几个数字。感受流程控制, 新手写流程控制时容易踩一些坑。第一个 if 条件后多加了一个分号,这会导致 if 语句提前结束,后面的大括号块会无条件执行。第二个 switch 忘记写 break 会导致穿透执行多个 case。 第三个, while 循环内没有更新变量会导致程序卡死。无限循环调试时可以使用打印语句输出变量。更推荐学习使用 id 的 断点调试, 可以逐凡观察程序执行流程,创建 common mistakes 类,展示常见错误。第一个错误, if 条件后多加分号, 导致打印语句无条件执行。第二个,死循环已被注视掉,防止卡死。调试技巧演示了打印循环变量,记住这些小细节,能节省大量调试时间。 编程学习,只看不练等于白学。请你务必打开自己的 id, 把今天所有视力代码亲手敲一遍,试着修改条件或循环次数,观察输出结果的变化。 可以给自己出个小题目,比如模拟一个简单的 atm 取款机,用到 f 判断余额和 do。 while 循环流程控制式编程基本功, 敲得越多,代码感觉越自然。如果觉得视频有用,欢迎收藏,方便以后随时复习翻阅。感谢你的观看,我们下个视频再见!

道题呢,是来自于阿里巴巴的一道八月份的面试题啊,说是介绍几个常用的 start, 我 们都知道啊, start 其实是我们 spring boot 开放的一个功能啊, 它可以集成第三方的一个 start 来完成我们项目的一个集成啊。这道题主要考察的是你对于 spring boot 的 一个 start 的 一个理解啊,而这道面试题呢,在面试中高级加了开发工程师的时候会问到对应的薪资呢,是十五到二十五 k 的 这样的一个区间。 然后呢,我们来看一下,我在这里其实猎取了五个这样子的一个 start 啊,常用的 start。 那 么首先第一个呢,是 spring boot start web 它提供的是 web 开发所需要的一个 serverlet 以及 gsp 的 支持,包括我们内嵌的一个 tomcat。 第二个呢,是 spring boot 的 一个 spring jpa, 很 很明显啊,它提供的是 jpa 八加上 hypernote 的 一个支持。第三个是 reddis 的。 第四个呢,是 mybase 集成我们的一个 start 所需要引的这样的一个公共的 start。 第五个呢,是我们的一个 solo 所需要引用的一个 start。 很 明显啊,除此之外,还会有比如说像你要引入 mq, rapidmq, 引入 es 等等等等相关的一些。而这个首先第一个啊,我想告诉大家的是, 这里面埋藏了两个点,第一个,他,你看你有没有用过这些主键,比如说你说你项目当中用的 release, 又用了 mq, 那 么 mq 的 start 你 应该是知道的。第二个, 有没有真正的去理解 start 这个东西,它到底是干什么的? ok, 所以 面试的时候注意这两个点就 ok 了啊。介绍几个常用的 start, 这道题完成, 不要为老板打工,而是为简历打工。不要说为了钱而打工,而是说你要为你的工作能力能够体现在简历上而打工。 哈佛大学呢,提出了跳槽经济,越是跳槽经济蓬勃发展的这个时候呢,其实是越需要你的职业规划,职业规划呢,目标做的比较好的人, 他完全可以在连续的几次跳槽之后呢,能够更快的达到他自己的职业的最终的那个目标。所以咱们小伙伴们呢,不要再想着说你是在为老板打工,也不是在为钱而打工,而是为了你最终的那个目标,为了你的能力能够体现在简历上而打工。关于跳槽经济学呢,我觉得有几点 他非常的重要。第一个呀,你一定要进行战略上的准备,就是你想清楚自己的长远目标啊,想清楚说自己呢,最终你这辈子要成为什么样的人,你记住所有的战术都要服务于战略。第二个呢,你要了解啊,你目前到底面临的是什么样的具体的困局, 要想清楚跳槽这件事是不是能够帮助你解决这个困局的唯一的出路。有的时候呢,你自己的公司有成长的空间,那你就未必一定要跳槽。 第三,一定要注意你商业价值的这个要素,提前呢,你要准备好技能,那怎么做呢?就是提前你进行市场的测试,比如说呢,你经常把简历啊给扔出去,然后看看市场的反馈,随时把控你自己在当前这个市场上具体的价值。到底是什么这个东西呢,是你保持竞争力的关键的关键。 第四个,就说你一定要了解你当前这份工作的寿命,尽量的专注于一直上升的行业。就是说你跳槽的话呢,一定是那种从夕阳行业跳往朝阳行业,当然啊,就这个呢,就需要你对行业呢有更深入的认知,就说你要多听听已经在行业里面待了很多年的人,这些人怎么说? 同时呢,我建议你多关注经济和时势,尽量的能够判断出一个新兴行业的他的发展趋势。第五,永远不要后悔跳槽,这是一个人实际上他消极态度的一个借口,无论结果如何, 你放松心态,正确面对。最后一个最好的下家在哪?我建议你使用呢最优停止定律啊,在合适的年龄找到最优的下家。

my botis 插件机制是其最强大的扩展点之一,虽然我们平时可能更多的是使用现成的插件,但在一些特定的场景下,自己动手写一个插件能解决很多复杂的非业务性的需求。今天我们就来探讨 my botis 插件的一个原理,以及如何去手写一个自定义的插件。首先明确一个概念, my botis 插件本 上是一个拦截器,它利用 g d k 的 一个动态代理的技术介入了 mybot 的 核心对象的执行流程,让我们有机会去修改方法的执行。 mybot 的 允许我们拦截四大核心对象,第一个一个交点执行器,负责 c 库的一个执行。第 第二个呢是 statement handle 了处理细口语句的预翻译和参数的设置。第三个 prime handle, 处理参数的一个映射。第四个, result handle, 处理结果级的映射。如果你还在盲目刷题,不知道面试到底考什么,我已经把简历优化模板、八股文高频题目、面试全流程应对策略、突击学习路线图全 都打包整理好了,覆盖从投递到谈心的每个环节,需要的评论区扣六六六直接领走。实现一个自定义的插件通常只需要简单的三步,第一步是实现 intercept 的 接口,这里面最重要的是 intercept 方法,你的核心业务逻辑就写在这里。第二步呢,是添加注解,使用 intercept 的 注解和 signature 的 注解,明确指定 my bots 你 要去拦截哪个对象的哪个方法,例如这样就表示拦截执行器的 update 方法。第三步,注册插件,在 my bots 配置文件或者 spring boot 配置类里面 去将该插件注册进去,那么我们在实际工作中通常如何去应用插件呢?这几个经典的实战场景。场景一, c 股的一个性能监控慢查询日制需求是需要去统计每个辛苦的一个执行时间,找出慢查询。实现方式是拦截 excel 的 一个 update 和 汇率方法,在方法执行前记录时间戳,执行后计算号时如果超过预值,则打印告警日记及完整的一个 sql 的 一个语句。场景二,数据自动填充需求是每次插入或者更新数据时,自动填上 create time update time, create by, update by 这些字段,避免手动去 set。 实现方式是拦截 exact 的 一个 update 方法,在西果的一个执行前,通过反摄获取参数的一个对象,自动给这些审计字段去复制。场景三,数据加密或解密需求是数据库里面的些敏感信息必须加密存储,但在业务代码中使用时需要是铭文。实现方式是写入时拦截 paramilien handler 的 一个 set parameters 的 一个方法,将参数对象中的一个敏感字段进行加密读取的时候呢?拦截 result set 函数的一个 handler result set 词的一个方法,将结果集中的一个密文解密和铭文效果是实现了对上层业务的一个透明化处理。总结下,买巴蒂斯的一个插件是基于动态代理的 一个责任链模式去实现的。通过拦截四大核心对象,我们可以极其灵活地去扩展 mybots 的 一个功能。无论是做性能监控、数据审计,还是分库分表、数据脱敏,插件机制都是我们的有效手段。掌握了插件开发,就意味着你深入理解了 mybots 这个底层行为。

来自于阿里巴巴的一道九月份的面试题啊,说是如何在 spring boot 启动的时候运行一些特定的代码,这个时候可能有些同学他就会比较懵逼了,他说老师,我为什么要在 spring boot 启动的时候运行一些特定的代码呢?实际上啊,我们这道题考察的是什么呢?他考察的是你 在比如说写到一些源码或者中间键的时候,有没有自己的一个理解啊? ok, 这道题主要考察的是个比如说我去自定义咱们的一个什么定时任务调度,那么这个时候呢,我们就需要把定时调度的这样的一个触发器啊,或者调度器的内去干嘛加入到 spring 的 spring 周期当中去, 那么这个时候毕竟必定我要就要把它加入 ioc 容器,对吧?那么这是一些写中间键的时候可能会遇到的一些问题啊, 那么这个题呢,是对应的是高级加号开发工程师,对应的薪资呢,是二十五到四十 k 这样的一个呃,区间啊,那么怎么去弄呢?实际上很简单啊,就当你去实现接口,比如说 application running, 或者说当你去实现 command link run 这样两个接口的时候,这两个接口实现方式是一样的啊,并且他们都只提供了一个 run 方法,并且我在课上啊,在定时任务调度课上是帮你们去实现了 command, 嗯, in run 啊,这样的一个接口啊,实现这些接口呢,就可以把这个类加入 ioc 容器当中啊,简单高效啊。 ok, 这就是这道题如何在 spring boot 启动的时候运行一些特定代码,你的一个回答啊, 不要为老板打工,而是为简历打工,不要说为了钱而打工,而是说你要为你的工作能力能够体现在简历上而打工。 哈佛大学呢,提出了跳槽经济,越是跳槽经济蓬勃发展的这个时候呢,其实是越需要你的职业规划,职业规划呢,目标做的比较好的人, 他完全可以在连续的几次跳槽之后呢,能够更快的达到他自己的职业的最终的那个目标。所以咱们小伙伴们呢,不要再想着说你是在为老板打工,也不是在为钱而打工,而是为了你最终的那个目标,为了你的能力能够体现在简历上而打工。关于跳槽经济学呢,我觉得有几点 他非常的重要。第一个呀,你一定要进行战略上的准备,就是你想清楚自己的长远目标啊,想清楚说自己呢,最终你这辈子要成为什么样的人,你记住所有的战术都要服务于战略。第二个呢,你要了解啊,你目前到底面临的是什么样的具体的困局, 要想清楚跳槽这件事是不是能够帮助你解决这个困局的唯一的出路,有的时候呢,你自己的公司有成长的空间,那你就未必一定要跳槽。 第三,一定要注意你商业价值的这个要素,提前呢,你要准备好技能,那怎么做呢?就是提前你进行市场的测试,比如说呢,你经常把简历扔出去,然后看看市场的反馈,随时把控你自己在当前这个市场上具体的价值到底是什么 这个东西呢,是你保持竞争力的关键的关键。第四个,就说你一定要了解你当前这份工作的寿命,尽量的专注于一直上升的行业,就是说你跳槽的话呢,一定是那种从夕阳行业跳往朝阳行业,当然啊,就这个呢,就需要你对行业呢有更深入的认知, 说你要多听听已经在行业里面待了很多年的人,这些人怎么说?同时呢,我建议你多关注经济和时势,尽量的能够判断出一个新兴行业的它的发展趋势。第五,永远不要后悔跳槽,这是一个人实际上他消极态度的一个借口,无论结果如何 啊,你放松心态,正确面对。最后一个最好的下家在哪?我建议你使用呢最优停止定律啊,在合适的年龄找到最优的下家。

大家好,呃,首先由衷感谢一下波面 app 给我们提供的这期非常精到的后端知识点,嗯,非常感谢,里面的解析确实非常硬核 对,所以今天呢,我们要为你彻底拆解一下好 spa jvm 里面的这个呃炸发对象头。没错,就是带你完全弄清对象在内存里的真实形态到底是什么样子的。 其实你可以想象一下啊,如果说把咱们平时写的扎巴对象呃比作是一个在系统里面到处流转的快递包裹的话,那个实利数据其实就是包裹里的货物。 对,你在写代码的时候肯定最关心货物对吧?但是底层的 jvm 这个庞大的分拣系统,它其实,呃根本不在乎你里面装了什么东西 哈,对,他不关心业务逻辑,他只盯着贴在盒子外面的那张多功能电子面单,所以今天咱们要聊的这个对象头就是这张面单。嗯,而且这张面单的存在意义真的是太大了,它是整个基础架构的基石, 你想想支撑你平时用的那些锁机制啊,还有底层的垃圾回收,或者是面向对象最核心的多肽分派,嗯,这些其实全都是依赖这张面单里记录的数据来实现的。 哇,那咱们现在就赶紧把这张面单撕开来看个究竟。里面最复杂的部分肯定就是那个叫 mark word 的 东西了吧?对, mark word! 而且让人觉得很不可思议的是, 在六十四位系统下面,它仅仅只占八个字节。等等,只有八个字节吗?这就让人很费解了呀,区区八个字节,你要往里面塞哈西码?还有那个呃 g c 的 分代年龄,甚至还有各种现成所的状态。是的,这里大家注意啊,是现成, 对,县城。这就好像是一把那种极其迷你的瑞士军刀,它怎么可能同时装下这么多东西?其实,呃,这就涉及到它非常核心的一个设计哲学了,叫做非固定动态数据结构。非固定就是说它会变。没错,为了把内存效率压榨到极致, jvm, 它其实不会为每一个状态去预留那种固定的空间哦,它会要 mark word, 根据这个对象当前的所状态,呃,动态地去附用自己的存存空间。动态附用,能具体举个例子吗?就拿面试里面极其容易被问到的一个细节来说吧, 分配给 g c 分 代年龄的空间被严格限制在了,呃,四个 bit, 仅仅四个 bit。 对 哦,我明白了,因为只有四个 bit, 所以 二近视最大,能表示的是近视数,就是呃,二的四次方减一等于十五。 完全正确。所以就直接从底层解释了为什么在 java 里面,一个对象默认晋升到老年代的最大年龄只能是十五。没错,你不能再大了,因为底层根本存不下。这就是底层存储结构倒逼上层业务逻辑的一个典型体现。原来是这样,太巧妙了, 那锁状态呢?锁状态的空间附用就更有意思了,当一个对象处于无锁状态的时候,它的标志位是零一。嗯,零一。这个时候呢?它内部大部分的空间存的其实是哈西码, 但是一旦发生了非常强烈的锁竞争,也就是升级成重量级锁了。对,升级成重量级锁之后,标志位会直接跃迁为一零。而这个时候,原本存哈西码的那个空间就会被直接抹去, 等下直接抹去,那这八个字节现在装的到底是什么东西?它的内部结构这个时候会进行一个彻底的重组, 它会生成一个六十二个 bit 的 指针,指向哪里?直接指向一个叫 object moniker 的 管城对象。哇,哎,这就从底层机制上解释了另一个面试高频问题了, 你知道是什么吗?呃,是不是那个?为什么 java 里任何对象都能当锁?没错,就是因为每一个对象的面单里面都天生具备这种动态变身为重量级锁指真的能力。这个动态变形的设计确实是绝了, 不过那个如果面单上只记录了对象自己的状态,那 jvm 怎么知道这个快递到底是哪个厂家发出来的?就是说,他怎么知道这个对象属于哪个类?问到点子上了,这就需要对象头的第二部分出场了,也就是 class pointer 类型指征。嗯, 类型指征这个指征就是用来定位对象所对应的类元素距的。在六十四位架构下,它本来应该是占八个字节的,但是,但是面试肯定不考这个正常情况,对吧?哈哈哈,好, 实战和面试的考点在于,现代 jvm 默认是开启了指征压缩的哦,压缩了之后呢? 压缩之后,它实际上只占用四个字节,只要四个字节。那如果我这个对象是一个树组呢?我记得 jvm 好 像没法像对待普通对象那样,直接通过类元数据去推断出动态树组的大小吧?你这个逻辑非常灵敏。 确实是这样,所以我们要特殊对待树组。如果是树组的话,对象头里面必须要多出一块东西,叫什么?叫 alex, 专门用四个字节来显示地记录数组的长度。哦,懂了,那其实如果大家现在正在为马上要来的后端面试做准备的话,把这些零散的知识点串联起来其实并不难。对,其实逻辑非常清晰。那个我来总结一下,你看对不对啊? 首先核心组成无非就是 mark、 word 和类型指阵,那如果是数组,就再多加一个四字节的数组长度,没错。然后计算大小也很顺理,成长了。 普通对下就是八字节的马克沃尔加。呃,四字节的压缩类型指针等于十二个字节。嗯,十二字节。然后为了满足 jvm 那 个八字节对齐的强制要求,会自动塞进去四个字节的填充,所以最后整体表现为十六个字节,完全正确。 如果是数组对象的话,就是八加四,再加四字节的数组长度直接等于十六字节, 连填充都不需要了。对,其实啊,你在面试的时候,把这种问题背景到核心组成,再到状态转化,最后是大小计算的逻辑链贯起来, 这正是面试官最想听到的,就是不仅能打出普通对象头和数组对象头的区别,还能讲透最大年龄为什么是十五对,包括对象为什么能作为锁,是因为重量级锁状态下指真的动态生成。 当你把这些都说清楚了,你就把单纯的是什么升华到了为什么和怎么做的高度,绝对会让人眼前一亮的。好,那为了让你在面试里彻底稳赢,我们现在直接给出五个最高频的面试题,并且直接给你标准答案准备好了吗?来吧! 第一题, java 对 象头包含哪些部分?答,包含 markword 类型指征,那如果是数组的话,还有数组长度,完美。第二题,为什么 java 对 象最大年龄是十五? 答,因为 markword 里面记录 g c 年龄的空间被严格限制为了四个 bit 没错。 第三题,为什么任何对象都能作为锁?答,因为在重量级锁的状态下, mark word 会生成指向管程,也就是 monitor 的 指针。第四题, 开启指针压缩之后,普通对象头有多大?答,十二字节加上四字节的对齐填充,总共占用十六个字节。最后一题, 述族对象头和普通对象头有什么区别?答,多出四个字节,用于寄宿述祖,长度非常利落,就是这么简单直接。 希望这期节目能帮你彻底拿下这个硬核考点。感谢你的收听,我们下次深度解析,再见!面试加油,下次见!

大家好,今天我们继续来看 macbook 的 面具 主键,所以唯一属于头发和手影的区别与联系。一、主键, 他的作用是唯一标准表中的每一行数据,因此图片不允许重复,也不允许维纳。一张表只能有一个图片 可以是多列组成的一个复合数矩阵。二、 所以我们先看普通术语,它的作用是加速裁缝没没有唯一性,约束也有所围绕。 一张表可以有多个普通术语。三、唯一术语, 它的作用是标识表中业或业组合的唯一性, 同时加速查询,因此为所欲,不允许重复,但允许为浪,并且浪子可以有多个。由此可见,它以普通所领的出 别在于标识了唯一性。与主体的区别在于,一、主体只能有一个,唯一首映可以有多个。二、 主体不允许为让唯一首映可以。 四、复合树影,它的作用是基于中立创建的树影用于优化身体的内的材质, 可以分为复合普通树影、复合维 e 树影和复合主见,其作用和体面三点相同。 我一直在注意的是,复合所有设计的采取必须遵守,遵守原则,否则所以会失效。 好了,今天的分享就到这里,感谢大家的点赞、评论和关注,我们下期再见!

欢迎收听,首先特别明谢播面 app 为我们今天的内容提供知识点。大家好,今天我们来深入聊一个扎瓦面试里头, 嗯,可以说是既经典又容易让人犯迷糊的概念。匿名内部雷,没错,尤其是现在有了拉们的表达式,很多人会觉得,哎,这个东西是不是过时了?对,但面试官偏偏就爱问。 所以我们今天的任务就是要搞清楚它为什么还这么重要,以及它背后到底藏着哪些面试官想听到的细节。嗯,我们会聊聊它是什么,为什么需要它,以及在哪些关键场景下,它仍然是无法被替代的。好的,那我们先从一个比较好理解的类比开始吧。 我总喜欢把它比作一个一次性的纸杯,哈哈,这个比喻很形象,就是你临时想喝口水,肯定不会专门去买个正经杯子,对吧? 用完就扔的一次性杯子最方便。匿名内部类就是代码而离的这种一次性纸杯,嗯,但问题就来了, 什么样的代码需求会简单到只需要一个用完就扔的一次性类呢?问到点子上了,这其实就说到了它的核心价值,一个是简洁,另一个是上下文关联。 简洁上下文管脸。对,你想想看,比如说你要给一个按钮加个点击事件,或者启动一个特别简单的后台现成,就像 runble 那 种。没错,这个实现逻辑可能就三五行代码,而且,呃,这辈子你可能只在这一个地方用一次,那专门为他建一个点 java 文件,确实是小题大盗了。就是这个道理, 匿名内部类就允许你把这个实现逻辑直接写在使用它的地方,这样代码读起来上下文特别清晰,一目了然。我明白了, 就是为了避免项目里到处都是那种只有几行代码的一次性类文件,让整个代码结构更清爽。是的,好,那我们来看看它的语法。 new supertype, 然后跟一对括号,一个大括号,最后再来个分号。这个结构我一直觉得有点奇怪。嗨,很多人都有这个感觉,它看起来像是在 new 一个东西,但后面又跟上了一个花括号,像是在定义一个类, 感觉是两种语法撞在了一起。这要怎么理解?你这个观察非常到位,它确实就是撞在了一起,因为它在同时做两件事哦,这里的 new 关键字,它并不是在创建 supertype 本身的实力哦, 它是在创建 supertype 的 一个匿名的看不见的子类的实力。然后呢,后面的那个花括号,也就是大括号,就是那个匿名子类的类体,你可以在里面重写方法哦, 所以最后那个分号也不能漏,因为整个东西其实是一个表达式,完全正确。所以我们常写的 new thread, 然后括号里一个 new runnable 和一个大括号那段代码, 我们创建的其实不是一个 runnable 对 象,而是一个实现了 runnable 接口的,但是没有名字的那个类的对象。哎,这么一说就通了吧?通了通了, 这种语法感觉很灵活,但一般越灵活的东西,规矩也越多。这里面肯定有面试官喜欢问的坑,对吧? 你这完全是面试官的思路了。哈哈哈,必须的嘛,你说到点子上了。这直接就引出了这个话题的必考题,为什么匿名内部类访问的局部变量必须是 final 或者事实上 final 的? 对, 这个规矩我上学时就背过,但一直没想太明白底层的为什么。嗯,它的根源在于生命周期不匹配生命周期。对, 一个方法执行完了,它里面的那些局部变量就从暂内存里消失了,对吧?对,贪占了嘛。但是你在方法里创建的那个匿名内部类的实力呢?它可能被传给了另一个县城,那个县城还在跑,所以这个实力对象还活在堆内存里。哦, 我好像有点感觉了。就是说,方法都结束了,变量都死了,但那个匿名类的对象还活着,还想用那个变量,这怎么办?这就是关键。 所以扎巴变异器就耍了个花招,它在创建匿名内部类使命的时候,会把那个局部变量的值复制一份,复制一份儿。对,作为成员变量存到匿名类对象里, 那为了保证这份副本和外面的原始值永远一致,避免数据错乱,扎巴干脆就规定这个局部变量不许再变了,也就是必须是 final 的, 这是一种安全机制。原来是这样, 为了保证数迹的一致性,编辑器直接冻结了一份值的快照给他用。这个解释比死记硬背清楚多了。 那么就是自然引出了他和 java 八 lamb 的 表达式的对决了。是的,这是另一个高频考点,用 lamb 的 写法。刚才那个 runnable 的 例子直接简化成一横,就是括号一个箭头,然后大括号简捷到极致。我的第一反应就是, 有了这么好用的工具,匿名累不累?是不是可以彻底退休了?这是一个非常核心的问题,但答案是不能。它们解决的场景其实不太一样。怎么说, luma 是 一个纯粹的行为,或者说函数的快捷方式?它有个硬性规定,只能用来实现只有一个抽象方法的接口,也就是我们说的函数式接口。它非常纯粹,就是一段代码逻辑。对。而匿名累不累呢? 它是一个珍重的对象,一个珍重的对象,完全正确。匿名内部类创建的是一个实实在在的对象实力,这意味着什么呢?第一,它可以继承一个类,甚至是抽象类, luma 做不到。 第二,它可以实现一个有多个方法的接口, luma 也做不到。嗯,第三,也是最容易被忽视的一点是机制。关键, 在匿名内部类里, this 指向他自己这个实力,而在 lamb 的 表达式里, this 指向的是外部类的实力。哇,这个区别很关键,所以可以这样总结吗? lamda 是 为了一次性的,无状态的行为而生的,非常贴切。而匿名类目是为了一个一次性的,但可能带有状态和多的方法的迷你对象而生的。这个总结非常精准。好的,那我们进入最后的快问快答环节, 帮大家巩固下今天的面试要点。第一个问题,什么是扎曼匿名类?布类,它是一种没有名字,只使用一次的类,可以在创建对象的同时定义类的实现,主要用来继承一个类,或者实现一个接口。好, 第二个问题,匿名类不类有什么优点?主要是代码简洁,作用域明确,避免了为那些简单的一次性实现去创建完整的类文件,非常好。 第三个也是最重要的,为什么匿名类不类访问的局部变量需要是 final 的? 因为局部变量和匿名内部类的生命周期不同,编一器会拷贝一份变量副本给内部类,为了保证数据的一致性,就规定这个变量不可变完美。 第四个,匿名内部类和 lambada 表达式的关键区别是什么? lambada 只能用于韩式接口,而匿名内部类可以继承类或实现任何接口。另外它们的 diss 指向也不同。匿名内部类还可以拥有自己的状态和多个方法。最后一个问题 举一个,必须用匿名内部类而不能用那么大的场景。当你需要继承一个抽象类并实现它的抽象方法时,或者需要在一个实现体中定义多个成员变量和方法时,就必须用匿名内部类。清楚了。 看来匿名内部类并不是一个过时的技术,而是在特定场景下依然不可或缺。再次感谢波面 app 提供的话题素材,也谢谢大家的收听!

java 是 一种面向对象的编程语言,由 james gosling 在 sun microsystems 公司开发,一九九五年正式发布。现在 java 由 oracle 公司维护,每半年发布一个新版本,长期支持版本。 lts 更推荐用于生产环境。 java 最大的特点是跨平台,即同一份 java 程序可以在 windows、 mac、 linux 等不同操作系统上直接运行,无需修改代码。 跨平台的秘密在于, java 虚拟机简称 jvm。 java 原代码翻译后生成的是自解码文件 class, 而不是机器码。不同平台的 java 负责将自解码解释或翻译为本地机器码执行。 java 还具有安全性、高杀伤机制、自动内存管理、垃圾回收、 g c 不 需要手动释放内存、丰富的标准内存和内置多线程支持等优点。 注意, java 版本命名有变化, jdk 八十一、十七、二十一是常见的 lts 版本,建议学习时使用 jdk 二十一或更高 lts, 企业级后端 android 应用、大数据框架如 hadop 都广泛使用 java。 开发 java 程序必须先安装 jdk, 即 java development kit, 它包含编解器 java 和虚拟机 java 不要只安装 gre 运行环境,因为 gre 没有编解器。 推荐下载 jdk 二十一 lts 版本可以从 eclipse adoptium 或 oracle 官网获取。安装时请记住安装路径,例如 c 冒号反斜杠、 program files 反斜杠、 java 反斜杠。 jdk 二十一后面配置环境变量会用到 配置 java 下划线 home 环境变量,在系统变量中心键变量名 java 下划线 home 变量值为 gdk 的 安装根目录,不要包含并目录很多 java 工具,如 maven tomcat, 依赖这个变量。 再将百分号 java 下划线 home 百分号反斜杠,并添加到 path 环境变量中。 path 中要使用英文分号分隔多个路径,这样在任何目录下都可以直接使用 java 和 java 命令。 打开命令行 c, m, d 或 power shell, 输入 java version 和 java version。 如果显示正确的版本号,说明环境搭建成功。常见错误, java 下划线 home 路径写错, path 中忘了加百分号。 java 下划线 home 百分号反斜杠并 我们来编写第一个 java 程序。创建一个文本文件,命名为 hello world。 java 注意扩展名必须是 java 文件名要与公共类名完全一致,包括大小写。 使用 public class hello world 定义一个公共类,一个 java 文件中最多只能有一个 public 类,且文件名必须与该类名相同。 然后定义 public static void main string arcs 方法,这是 java 应用程序的入口点, jvm 会从这里开始执行。 public 表示可被外部调用, static 表示无需创建对象即可执行。 void 表示无返回值。 方法内的 system outprint hello world 用于在控制台输出一行文本,注意 print 会自动换行,如果不想换行,可以用 print 翻译。在命令行执行 java hello world, java 会生成 hello world plus 自解码文件。运行 java hello world 不要加 plus 后缀,控制台就会打印 hello world。 如果出现找不到主类错误,检查类名是否正确且包含 main 方法。 在 java 中,变量必须先声明后,使用声明时需指定数据类型和合法的变量名。变量名建议使用小写驼峰命名法,例如 student name int h 声明了一个整形变量 h, 此时 h 没有被出示化,它的值是默认值零。仅对于成员变量,局部变量必须显示出示化,否则翻译报错 h 等于二十是赋值语句。将整数值二十存入 h 变量也可以在声明的同时出示化,如 double price 等于九点九九,声明一个双精度浮点数,并复制为九点九九。 注意,局部变量方法内声明的变量在使用前必须显示出式化,如果只声明不赋值,变异会报可能尚未出式化变量的错误,这是 java 的 安全机制。 最后使用 system outprint 输出 h 和 price, 屏幕上会显示二十和九点九九。变量名区分大小写。 h 和 h 是 两个不同的变量。 java 有 八种基本数据类型, byte、 short、 int, long、 float、 double char, boolean, 它们直接存储数值,效率高。 整数类型中最常用的是 int。 三十二位浪类型,需要在数值后加 l 后缀,例如幺零零零零零 l, 否则会被当作 int 处理。浮点型默认是 double, 要定义 float, 必须加 f 后缀。 布尔型 boolean 只有两个值, true 和 false, 不 能像 c 语言那样用零或易代替字符型。叉二用单引号包围,只能存放一个 unico 字符。例如 a 中 stream 不是 基本数据类型,它是一个类引用类型。但因为使用极其频繁, java 提供了语法堂。如双引号直接创建 stream, 对 象不可变,任何修改都会生成新对象。 使用加号可以连接字母串和其他类型,会自动转换为字母串,输出结果。视力 java 成绩 true。 注意,叉二类型在运算时会提升为 int, 需要小心类型转换 算数。运算符包括加星号、百分号,其中除法和取模百分号需要特别注意。当两个操作数都是整数时,执行整数部分不会四舍五入, 例如,十除以三的结果是三,而不是三点三三三。如果需要精确结果,必须至少将一个操作数转换为负点数。 取模运算,负百分号返回余数百分之十三等于一。取模结果的正负与被除数相同,例如,负百分之十三等于负。一。 强制类型转换使用类型语法,例如 double a, 将 a 转换为 double 类型。注意强制转换可能丢失精度,如 double 转 int 会截断小数。 实践经验进行除法运算前,考虑是否需要浮点结果,如果需要,建议将其中一个操作数写为浮点字面量,如十点零斜杠三。或者使用强制转换整形运算,不会抛出除零异常除零会抛出 arithmetic exception。 关系运算符,用于比较两个值,结果是一个布尔值。常见的有等于等于等于等于等于不等于。注意,不要将等于等于误写为等于负值。 f 语句根据条件决定是否执行某段代码,条件必须是一个布尔表达式,不能像 javascript 那 样自动转换类型。 如果条件为 true, 执行 if 后面大括号内的代码,否则跳过 if 快。 如果有 else, 则执行 else 快。 大括号即使只有一条语句,也建议写上,提高可读性,并避免悬空 else 问题。 else 与最近的 if 配对。如果有多个 if else 嵌套,使用大括号明确归属,例如, else if 可以 处理多个分支。 本例中 score 等于八十五, score 大 于等于六十为 true, 所以 输出及格。注意,招牌中不能写六十小于等于, score 小 于等于一百。必须拆分为两个条件,用于与连接 循环,用于重复执行代码快。 for 循环是最常用的循环结构,适合已知循环次数的情况。语法, for 初使化循环条件更新循环体 初步化部分, int i 等于一声明,并初步化循环变量,该变量作用域仅限于循环内部,循环结束后无法访问,避免命名冲突。 循环条件 i 小 于等于无,每次循环前判断为 true 则执行,循环体为 false 则退出循环。更新部分, i 加加在每次循环体执行后执行,通常用于增加或减少计数器。 注意循环条件不能缺少,否则会无限循环。三个部分都可以省略,但分号必须保留。例如 four 是 无限循环, 输出结果会显示第一次到第五次循环。实践中, four 循环常用于便利数组或集合,千万不要在循环体内修改循环变量,导致死。循环 数组是一种容器,可以存储固定数量的相同类型数据。声明方式,类型数组名。例如 int numbers 也可以写成 int numbers, 但前者更推荐 静态出式化,在声明时直接给出元素,如十二、十三、十四、十五十,也可以动态出式化。 int a r r 等于 new int。 五,创建长度为五的数组,元素为默认值零, 通过下标访问元素,下标从零开始,因此第一个元素是 numbers 零,最后一个元素是 numbers numbers。 length 一 访问超出范围,会抛出 array index out of bounds exception 数组的 length 属性返回元素个数。注意不是方法,所以不要加括号。数组创建后长度不可变, 通常使用 for 循环变量。循环变量从零到 length 一 java 无引入了增强 for 循环 for h 语法更简洁,但不能获取下标。 方法 method 用于封装可重复使用的代码块,提高附用性和可维护性。方法有五要素,修饰符、返回值、类型、方法名、参数列表、方法体。 这里定义了一个静态方法, a 修饰符 public static 返回值类型 int 方法名 add 参数列表 int a int b。 方法体,返回 a 加 b。 在 main 方法中调用 add 五到三的开区间五和三式实参按顺序传递给型参 a 和 b。 java 只有值传递,传递的是基本数据类型的副本,或引用类型的地址副本。 方法执行到 return 语句结束,并将返回值返回给调用者。如果方法没有返回值,返回值类型写 void, 可以 省略 return 或写 return 提前结束。 注意,方法名采用小写驼峰命名,如 add numbers。 静态方法可以直接用类名调用,本类中可省略类名。主方法 main 必须写成 public static void main stream arcs 参数名 arcs 可以 改,但类型和形式固定。

欢迎收听,首先还是要特别感谢波面 app 为我们这次的探讨提供了非常详尽的解析材料。嗯,今天啊,咱们来聊一个扎瓦面试里头可以说是绕不开的一个硬核知识点。 内存屏障确实很硬核,简单来说,它就是保证多县城代码不出错的底层关键技术, 专门解决 cpu 为了追求速度结果引起的两个大问题,数据不同步和指令乱序。嗯,像我们常用的 volatile 和 synchronize 的 关键字,其实它们的魔力背后就是内存屏障在起作用。对, 所以我们这次的目标就很明确,就是帮你彻底搞懂它,让你在面试的时候能把这个复杂的问题讲得清清楚楚。 那咱们就从问题的根源开始吧。好,我觉得可以这么想啊,你和你同事就是两个县城。嗯,这个比喻可以,你们俩在各自的电脑上,这个电脑呢,就是 cpu 的 核心,然后你们再编辑同一份儿共享文档,这份儿文档就是主内存。嗯哼,为了快嘛, 你们肯定都先把文档复制到本地桌面,也就是 cpu 款式上修改。对,这时候问题就来了,如果你改了内容,但没立刻同步,那你同事看到的不就还是旧的版本吗?这个应该就是所谓的可见性问题吧。哎,这个比喻一下就抓住了核心。 从基础上讲呢,并发编程的这些意外主要就来自两个根源。第一个就是你说的 cpu 款式导致的可见性问题, 每个核心都有自己的高速缓存修改先发生在款式里,但他什么时候写回主内存这个事他不确定啊。所以一个核心矮了,另一个核心可能根本就看不见,就是这个意思。然后还有第二个根源叫有序性问题。 为了效率,编解器和 cpu 会自作主张地打乱你代码的执行顺序,这个就叫指令重排序等等。指令重排序?这听起来有点吓人啊。就是说我写的代码执行顺序都不能保证了。在单县城里,你放心,没问题, 因为优化的前提就是不能改变单线城的最终结果。但在多线城下,这个就可能出大事了。比如,比如你写了两行代码,第一行 a 等于一,第二行 flag 等于 true, 你 的预期是,另一个县城看到 flag 是 true 的 时候, a 肯定已经是一了。对啊,理应如此。 但如果发生了重排序,第二行可能先执行了,那另一个县城看到 flag 是 处跑去读 a, 结果读到的还是旧值零。你看程序不就出错了吗? 我明白了。所以 cpu 这些性能优化反而成了多线城编程的陷阱。那么内存屏障就是来填这些坑的,它具体是个啥?对, 你可以把它想象成一个交通警察,它就在代码里划下一条线。交通警察有意识,嗯, 它会告诉 c、 p、 u 和变易器到这儿停一下,线前面的指令不许跑到后面去,线后面的也别往前凑,并且立刻把你手头魂线里的修改更新到总部,也就是主内存。所以它的核心作用就两个, 没错。总结一下就是,第一,禁止指令重排序,解决了有序型问题。第二,保证内存可见性, 写操作的时候强制刷新缓存,到主内存读操作的时候强制让本地缓存失效,去主内存读最新的,这就解决了可见性问题。好,那我们写 java 代码的时候,需要我们自己手动去插这些交通警察吗? 哎,这问到点子上了。好消息是,我们不需要。 jvm 已经帮我们做好了,我们只要用特定的关键词就能召唤它们,比如说 volatile。 对, volatile 是 最典型的例子, 你对一个 volatile 变量进行写操作,它后面就会跟一个很强的 store load 屏障,强制把新值刷到主内存。你对它进行读操作,它就会用 load load 这类的屏障让你的本地缓存失效,必须从主内存去读。 哦,原来是这样,这就是它保证可见性和有序性的原理。但你得记住,它不保证原则性。那 synchronize 呢? synchronize 的 就更重量级了,它在进入代码块的时候会插入 load 柄账清空工作,内存 退出的时候插入 store 屏障,把所有修改刷回去。所以它能同时保证原则性、可见性和有序性蒙免,从最底层保证了病发的正确性,这是展示技术深度的机会没错。好了, 那我们接下来直接为你梳理五个关于内存屏障的高平面实体和回答要点来吧。第一个, 面试官问为什么需要内存屏障?嗯,你就这么答。为了解决现代多核 cpu 架构里因为 cpu 缓存导致的可见性问题,以及因为指令重排序优化导致的有序性问题,这两者都是并发并成正确性的核心挑战很清晰。 第二个,沃尔泰关键字是如何利用内存屏障保证可见性和有序性的啊?它通过在对变量的读写操作前后插入特定的内存屏障来实现 写操作后叉, store load 屏障强制刷新到主存读操作前让本地缓存失效,强制从主存加载。 这一系列操作就确保了一个现象的修改,对其他现象立即可见,并且禁止了相关的指令重排。明白 第三问, volatile 和 synchronized 在 内存可见性上有什么区别? volatile 指保证单个共享变量的可见性,而 synchronized 呢,它保证的是整个代码块里所有共享变量的可见性。 它范围更广,通过进入代码块时差屏障来做更大范围的数据同步。好的第四个,什么是指令重排序?内存屏障如何阻止它?指令重排序是编码器和受理器为了提升效率,在不改变单线性结果的前提下,对指令顺序的优化。 内存屏障就像个栅栏,明确规定了屏障前后的指令不能相互跨越,从而保证了必要的执行顺序,非常好。 最后一个问题,能简单介绍一下 j m m 定义的四种内存屏障吗?可以有四种, load load store store load store 和 store load load load 保证读的有序性, store store 保证写的有序性, load store 保证读在写之前,而 store load 是 功能最全,开销最大的。它确保了之前的写对之后的所有读都可见,是实现 volatile 写的关键。好的,今天我们算是把 java 内存屏障 给彻底弄明白了,它就是 volatile、 synchronized 这些病发工具能够正常工作的底层基石。没错,面试的时候你能从 cpu 缓存和指令重排序这两个问题根源开始讲,再谈到内存屏障作为解决方案, 最后关联到 volatile 这些具体应用,这样的回答会非常有深度,也一定能让面试官对你刮目相看。感谢你的收听,我们下次再见。

今天面了一个宅瓦高级开发,简历上写着主导过云原生微服务全链路高可用设计,对大规模流量下的稳定性治理有丰富实战经验。我上来就问他,一个用户发起接口查询请求 到最终返回正常数据,这中间的全链路流程你详细讲讲。他清了清嗓子,嗯,前端请求到云原生网关,网关路由到对应微服务服务查缓存,查数据库 组装,结果返回前端展示数据。我点了点头,好,基础流程。对了,那我追问几个细节,第一,同一秒十万级请求涌入,怎么防止缓存击穿穿透压垮数据库? 第二,微服务调用链路过长,某个下游节点超时,怎么保证核心链路不被拖死?第三,云原声节点自动扩缩熔蚀怎么保证配置限流规则不丢失、不冲突? 第四,全链路出现异常,怎么快速定位故障节点,而不是盲目排查?缓冲一致性怎么保障?动态限流规则如何实时生效?链路监控靠什么指标告警? 服务伸缩时绘画怎么保持不中断?他彻底沉默了。这个回答就是典型的只会搭服务,不懂全链路稳定性之理。一遇到流量波动与云原声调度异常,完全没有体系化应对思路。 这道题是二零二六年大厂 java 后端面试的压轴题,考察的是你对云原声弹性、缓存、智力、熔断、限流、全链路可观测性的综合理解。想拿高分,必须分环节讲出险境和对策。 如果这道题目你也不会回答的话,我整理了让大厂 hr 沉默的必考题库,含改 g e v m 夺命连环问 spring 灵魂八谷高并发必杀惩戒睿思深度陷阱点个赞,评论区甩六六六,打包带走 nice 阶段一,网关入口层流量治理的第一道闸请求,首先到达云原深 a p i 网关,面试官想听的不是简单路由,而是流量管控与安全防护 前进突发流量红风恶意请求,非法访问,直接冲击后端服务。对策,动态限流,基于 qps 并发述客户端标识作多维度限流,超出预值直接优雅降级,不影响核心服务 安全拦截,开启参数校验访问,健全恶意 ip 封禁,从入口过滤无效请求,减轻后端压力。 规则热更限流路由,健全规则,支持实时热更新,无需重启网关即可生效,适配多变场景。阶段二,微服务业务层稳定性保障的主战场,多服务依赖调用,核心是防堵塞、防血崩、保数据一致。 险境服务调用超时急连故障缓存与数据库不一致,重复请求对策,熔断降级,对下游若依赖设置熔断策略,异常时自动跳闸走兜底逻辑,不堵塞核心流程。 缓存治理,提前防范缓存穿透,击穿血崩,采用缓存预热护翅锁,过气时间随机化。策略, 数据一致性读写分离加最终一致性方案查询,优先走缓存异常回原数据库,保证数据准确调用。安全服务间调用,开启重试,超时控制,同时做密等校验,避免重复处理导致数据异常。 阶段三,可观测与中间渐层故障定位的透视眼大规模微幅无下,看不见问题就解决不了问题。险境故障无感知炼录耗时不明异常无告警问题,定位耗时极长。 对策,全链路追踪,对每一次请求做链路买点,实时监控各服务耗时状态,快速定位。瓶颈节点监控告警,基于 cpu 内存错误率、延迟等核心指标配置,告警策略亦成第一时间通知。 日制中心化统一采集业务日制异常日制知识关键词检测与聚合分析,提升排查效率。异步结偶,非核心逻辑,通过消息队列异步处理,不占用核心电路资源,避免同步堵塞。 阶段四,云原生弹性层道道应对洪峰的自动调节器传统静态部署无法适配云原生下的流量突变险境, 流量突增导致服务资源不足,节点宕机扩缩容不及时。对策,自动扩缩容,根据 cpu 利用率、请求量等指标配置。弹性策略,流量上涨自动新增,实力回落时自动缩容。 多实力容灾服务多副本跨口用区部署,避免单点故障导致整体功能不可用。配置统一管理,使用配置中心集中管理,配置扩缩容时,新节点自动拉取最新配置,避免规则冲突。资源隔离, 核心服务与非核心服务做资源隔离,防止资源争抢影响核心接口可用性啊,这个就叫专业。 最后来波灵魂总结,所以下次面试官再问你,云源生下全链路请求处理,你要分环节讲出问题和解决方案。 网关入口层动态限流加安全拦截加规则热根,守住入口防线。微服务业务层融断降级加缓存治理加调用安全,保证核心链路稳定可观测。中间建层 链路追踪加监控告警加异步结偶,实现故障可查,风险可控。云原生弹性层自动扩缩,容加多,副本容灾加配置统一从容应对流量红风与节点波动,这才是大厂高级后段要的 全链路稳定性治理与云原生架构深度思考。想学啊你,我教你啊!

召唤注解原理,很多同学呢,都会被问到,只会说反射,这种回答直接暴露你没看过原版,也很难拿到大厂的 offer。 我 们天天写艾特奥特贝尔,艾特 override, 你 可能以为是注解决定了业务逻辑,其实呢,不是,注解本身呢,就是一个哑巴标签,他不包含任何的业务逻辑,也不会主动执行任何操作。为一的作用呢,就是标记,等着编辑框架或者是运行时环境看到这个标记后呢,去做相应的处理。 理解注解的核心啊,首先要搞懂它的生命周期,这个由 adaptation 这个原注解来制定,一共分三集,牢记这三点,面试就赢了一半。 另外啊,针对还在准备面试的同学呢,我整理了一份面试核心资料,不只是注解,像身份页、 spring 新欢、依赖马斯克、索引优化等等这些高频的考点啊,从回答思路到项目表述,都拆解成了可以直接用的面试语言。 评论区留言六六六,免费分享给你啊。第一级, sos 级别,只存在于原码里,翻译完成后呢,就会被丢弃, 呃,最典型的就是艾特 overit, 用来这个教员方法重写,翻译完呢就没它的事了。那第二级呢,就是 class 级别,会被记录在 class 文件中,但 gm 加载 class 文件时呢,会忽略它,不会把它加载到内存里。第三级呢,就是 runtime 级别, 会永久的保留,运行期间呢,可以通过反射读取到,也是我们日常开发中最常用的级别。这里有个经典的误误区啊,很多人以为呢, spring 的 艾特 osware 的 依赖注入呢,是靠反射读取注解实现的, 所以它必须是 runtime 级别,其实不对,我们看原码就知道了。 at runtime 确实是 runtime 级别,但是 spring 处理它呢,主要不是在运行时靠反射,而是在容器启动时通过字检码增强,或者是后置处理器提前扫描和处理它。面试时呢,说清这一点,非常加分 儿。再说说怎么定义一个注解,很简单,用 at in the face 关键字就可以。在定义的时候呢,需要用到圆柱形和 at get aturation 呢?指定生命周期 at the top 呢?指定注解能用到什么地方?比如类方法字段上。如果面试官问你注解原理,一个完整的回答要包含三层,记住这个模板能访客为主哈。第一呢,就是本质论,注解是原数据标签自身没有任何逻辑。第二呢是生命周期论,说清 sauce、 class, runtime 三个级别, 以及只有 runtime 级别能被反射读取。第三呢,就是实现机制的强调,处理,注解的不是注解本身,而是变异器、工具或者框架。另外注意啊,面试官最喜欢追问的一个实战场景,比如如何自定义这注解实现日制脱敏,或者在 a o p 中怎么获取私有方法的注解参数, 把底层原理讲清楚,再结合实战场景的一些延伸,面试官会觉得你真的有经验,而不是被扒骨问。其实注解的原理啊,并不难,难的是跳出只说反射的误区,掌握他的生命周期和框架处理逻辑,把今天讲的这些搞明白,下次呢?面试被问注解原理,轻松访客为主,打动面试官。