自定义博客皮肤VIP专享

*博客头图:

格式为PNG、JPG,宽度*高度大于1920*100像素,不超过2MB,主视觉建议放在右侧,请参照线上博客头图

请上传大于1920*100像素的图片!

博客底图:

图片格式为PNG、JPG,不超过1MB,可上下左右平铺至整个背景

栏目图:

图片格式为PNG、JPG,图片宽度*高度为300*38像素,不超过0.5MB

主标题颜色:

RGB颜色,例如:#AFAFAF

Hover:

RGB颜色,例如:#AFAFAF

副标题颜色:

RGB颜色,例如:#AFAFAF

自定义博客皮肤

-+
  • 博客(74)
  • 收藏
  • 关注

原创 数据结构与算法(Java语言)之 并查集

另一个是10个元素但是是倾斜二叉树,或者说极端一点退化成一个链表的数结构,这样的话其实我们应该把100个元素的挂在倾斜的10个元素的集合上,这样我们的树结构高度才不会进一步倾斜。其实它主要解决的是我们有一个主要集合,里面有很多元素,我们现在要快随判断这些元素一共有多少组,也要快速返回每一个元素属于哪个组的问题。版本二的 union的时候,要更改的只有一个元素,p节点的代表节点改成q节点的代表节点。union的时候,我们不考虑每个子集合元素的多少,都是取右边元素为新的子集合的代表节点。输入:grid = [

2024-12-07 15:35:56 1525 18

原创 Java垃圾回收番外篇

Stop-The-World 是指在计算机系统的执行过程中,发生的全局暂停现象。当 STW 事件发生时:所有应用线程被强制挂起: 正在执行用户代码(你的业务逻辑)的线程会立即停止运行。系统仿佛“冻结”: 整个应用程序对外表现为完全无响应状态,无法处理任何新的请求或进行任何计算。特定任务独占运行: 在这段暂停期间,通常是垃圾回收器 执行关键任务,但也可以是其他需要全局一致视图的低级操作(如某些 JVM 内部操作、安全点更新等)。

2025-07-07 21:41:02 1868

原创 Java代码执行过程

解释器:保障跨平台性和快速启动,但性能低。JIT 编译器:运行时编译热点代码,换取接近原生的性能。协作哲学:“启动阶段用解释器快速执行,运行中逐步编译优化热代码” —— 在跨平台与高性能间取得完美平衡。

2025-06-27 22:37:15 1579

原创 对象实例化内存布局与访问定位

当虚拟机需要创建对象的时候,首先判断这个创建对象的指令的参数,能不能在常量池中找到对应的类的符号引用,并检查符号引用所代表的类是不是已经被加载 解析 初始化;引用类型的属性(如对象、数组),浅复制仅复制指向该子对象/数组的内存地址(引用),而不是在内存中创建一个全新的副本;优点:对象移动安全:GC 移动对象时只需更新句柄中的实例指针,栈中引用不变;内存分配结束之后,申请到的空间的值不是固定的,所以拿到内存空间之后,还需要初始化内存空间,这一步将分配到的空间都初始化为0。大小:32 位 JVM:4 字节;

2025-06-25 17:51:00 1257 1

原创 Web中的会话控制

答案是肯定的,我们可以在服务器端为每次会话创建一个对象,然后在这个对象中保存相关的信息。实际上 服务器会给我们创建的对象设置一个id,这个id是独一无二的,当请求到来的时候,我们服务端将这个id保存到Cookie中,这样后续的请求自动携带Cookie,服务器再通过Cookie中的id值就可以找到我们创建的对象。这就导致了,如果我们在Java Web程序中,登录了账号,下一次重新发起请求,服务器并不会认为新发起的请求是哪个用户发起的,这就需要每一次发起请求的时候都需要重新登陆,这样用户肯定是不接受的。

2025-06-23 16:57:35 1033

原创 Java虚拟机 -方法调用

从栈的角度,方法退出,实际上是当前栈帧出栈,要恢复上层方法的局部变量表与操作数栈,如果有返回值,还需要把返回值压入操作数栈,然后将程序计数器指向上层方法的下一条指令的地址。虚方法是支持动态绑定(运行时绑定)的方法,具体调用的方法实现由对象的实际类型(运行时类型)决定。调用别的类的方法的时候,从字节码的角度,我们调用别的类的方法,字节码里面存储的是别的类的符号引用。但是JVM运行的时候,我们需要一个机制去把这个符号,转化成实际的引用的类方法的地址,这样我们运行的时候,才能够找到要调用的方法。

2025-05-22 21:01:24 857

原创 Java虚拟机 -虚拟机栈

Java语言由于跨平台性,所以指令集是以栈为基础设计的。每个线程创建的时候都会创建一个虚拟机栈,内部每一个栈都是由一系列栈帧组成,每一个栈帧又对应了一个方法调用。虚拟机栈跟数据结构中的栈有类似的特点,都是先进后出,只支持入栈与出栈两种操作。另外栈是线程私有的。

2025-05-21 22:09:32 880 3

原创 Java虚拟机 - 程序计数器和虚拟机栈

Java运行时数据区作为JVM在程序执行过程中管理内存的核心结构,主要包括方法区(存储类元数据、运行时常量池、静态变量)、堆(存放对象实例和数组,被所有线程共享且是垃圾回收的主区域)、虚拟机栈(每个线程私有,用于存储方法调用的栈帧,包含局部变量表、操作数栈及方法出口)、本地方法栈(支持Native方法调用)和程序计数器(记录当前线程执行的字节码位置,确保多线程切换后能恢复执行)。JVM在运行期间把它管理的内存分为若干个区域,有些区域是线程私有的,有些区域是共享的。

2025-05-20 17:02:41 651 2

原创 tomcat

定义:Apache Tomcat 是一个开源的 Java Servlet 容器和 Web 服务器,用于运行 Java 应用程序。历史:Tomcat 的起源和发展历程。主要功能:支持 Servlet 和 JSP 技术,提供 Web 服务。

2025-05-18 17:10:15 927

原创 Java虚拟机 - JVM与Java体系结构

Java 自 1995 年由 Sun Microsystems 发布以来,凭借其 跨平台能力、面向对象特性 和 丰富的生态系统,迅速成为全球最流行的编程语言之一。而 Java 虚拟机(JVM)作为 Java 技术的核心引擎,通过“一次编写,到处运行”(Write Once, Run Anywhere)的理念,彻底改变了软件开发的模式。我们本章简单介绍一下Java语言与JVM的结构,之后我们会在专栏文章中,逐步把我们上面介绍的知识点都覆盖到,争取能够做到让大家能够对JVM的知识有一个宏观的认识。

2025-05-18 16:43:09 1306 1

原创 thinking in java - 泛型2

虽然ArrayMaker的kind参数通过Class保留了类型信息,但Array.newInstance的返回类型设计为Object,因为它需要支持所有可能的componentType(如String.class、Integer.class等),无法在编译时静态绑定到具体类型。当通过反射创建数组时,返回的实际类型(如String[])在运行时是明确的,但编译器无法验证其与泛型类型T[]的兼容性,因此需要显式强制转换。其实泛型,本身就是为了,让我们的代码能够处理多个类,让代码更加具有泛化能力。

2025-02-23 23:02:23 301

原创 thinking in java - 泛型1

而使用泛型方法的时候,通常不需要我们指定具体的参数类型,因为编译器会通过类型推断帮助我们找到具体的类型,这也叫类型参数推断。所以当我们调用泛型方法的时候,我们可以像普通方法一样调用即可,但是注意如果传入基本类型的时候,编译器会使用自动打包,将基本类型的包装类型传入。但是有的时候,限制我们的参数在一个派生组合里面,也非常限制我们的代码的扩展性。Java泛型是通过擦除来实现的,这意味着,当我们使用泛型的时候,实际上所有的类型信息都被擦出了,你唯一知道的是我们在使用一个对象。聪明的你,也许会相到接口。

2025-02-23 22:25:22 613

原创 【从字节码的角度看switch-case】

虽然Java的语法,switch-case语句是用来处理条件判断的。Java编译器会根据case值的分布情况,生成两种不同的字节码指令:tableswitch(表跳转)和lookupswitch(查找跳转)。当我们的条件比较多的时候,我们一般就不采用if-else的判断方式来进行判断了。执行效率高(时间复杂度 O(1)),但占用空间较大(需为所有可能的索引值分配表项)。适用场景:当case的值稀疏不连续(如 1, 10, 100)时使用。适用场景:当case的值连续且密集(如 1, 2, 3)时使用。

2025-02-18 20:50:17 386

原创 比简单工厂更好的 - 工厂方法模式(Factory Method Pattern)

产品接口(Product):声明了所有具体产品必须实现的操作。所有的具体产品类都实现了这个接口或继承自这个抽象类。具体产品(ConcreteProduct):实现了Product接口,提供了具体产品的实现。@Override@Override创建者/工厂接口(Creator):接口或抽象类,声明了工厂方法,该方法返回Product类型的对象。创建者还可以包含其他业务逻辑,这些逻辑可以调用工厂方法来创建产品对象。// 工厂方法// 其他业务逻辑// 使用创建的产品。

2025-01-21 22:40:25 1613 1

原创 少一点If/Else - 状态模式(State Pattern)

环境类(Context):环境类拥有对状态对象的引用,并且提供了客户端访问状态的方法。它还负责管理状态的变化。抽象状态(State):这是一个接口或抽象类,声明了所有具体状态必须实现的方法。这些方法定义了不同状态下对象的行为。具体状态(ConcreteState):具体状态实现了State接口,每个具体状态类都包含了与该状态相关的行为逻辑。@Override// 改变状态@Override// 改变状态状态模式的优点。

2025-01-15 22:48:36 1697 2

原创 更灵活的对象之间的联动 - 观察者模式(Observer Pattern)

主题(Subject):主题接口声明了添加、删除和通知观察者的方法。它可以是接口或抽象类,具体主题实现类会实现这些方法,并维护观察者的列表。} } }List;具体主题(ConcreteSubject):具体主题实现了Subject接口,并包含有状态信息。当状态发生变化时,它会通知所有注册的观察者。// 状态改变后通知所有观察者。

2025-01-14 20:24:18 1321 9

原创 有时候还是需要后悔药的 - 备忘录模式(Memento Pattern)

发起人(Originator):发起人是一个包含有状态信息的对象,它可以创建一个备忘录,用来记录当前的状态;也可以使用一个备忘录来恢复其状态。} // 创建备忘录 public Memento createMemento() {} // 恢复状态 public void restoreFromMemento(Memento memento) {} }} // 创建备忘录 public Memento createMemento() {

2025-01-13 22:15:05 880 5

原创 还是开个会议吧 - 中介者模式(Mediator Pattern)

如果在一个系统中,对象与对象之间的联系呈现出一种网状结构的时候,这就会导致系统非常复杂。而我们的中介者模式可以使得我们对象之间的关系大量减少。所有的对象都跟中介者进行沟通。这样的话,对象之间的关系就会出现从网状结构转化成星形结构,减少了对象之间的耦合度。降低耦合度:通过引入中介者,减少了对象之间直接的依赖关系,使得系统中的对象更加独立。集中化控制:所有的通信逻辑都集中在中介者中,这有助于管理和维护复杂的交互过程。易于扩展:新增加的同事对象只需要实现同事接口,并注册到中介者中即可,无需修改现有的代码。

2025-01-10 17:28:24 1495 2

原创 开关不一定是开关灯用 - 命令模式(Command Pattern)

降低了系统的耦合度。新的命令可以很容易地加入到系统中。可以方便地实现对请求的撤销和重做。不过,命令模式也可能增加系统的复杂性,因为它需要引入许多新的类。如果系统比较简单,使用命令模式可能会显得过于繁琐。

2025-01-09 23:04:57 1558

原创 一个个顺序挨着来 - 责任链模式(Chain of Responsibility Pattern)

定义:使多个对象都有机会处理请求,从而避免请求的发送者和接收者之间的耦合关系。将这些对象连成一条链,并沿着这条链传递请求,直到有一个对象处理它为止。目的:解耦请求的发送者与接收者,提供一个灵活的方式来处理请求,支持动态添加或移除处理逻辑。责任链可以帮助我们降低耦合度;增加灵活性;可以帮助我们更好地组织代码。我们上面实现地责任链模式是类似与拦截器的那种方式。责任链还可以设计为一些别的方式。责任链模式一般适用于日志记录;审批流程等等。

2025-01-08 23:30:54 1122 12

原创 【Java从入门到放弃 之 final 关键字】

修饰基本类型的时候,代表的是修饰变量的值不能变化;修饰Object引用的时候,代表的是这个变量代表的引用不能改变(引用不能改变,但是引用指向的对象是可以改变的)Overriding 只会发生在父类非私有的方法中,上面代码案例中我们在最下面的子类把f()改成自己的实现,实际上这个方法是public,父类的是private;Java允许你用final 修饰参数列表中的形参,这个意味着,在这个函数中不能修改这个形参。因为我们没有获取私有方法的权限,这也就意味着,我们不能改变父类中的私有方法的实现。

2025-01-07 22:16:50 1476 3

原创 你内部啥样跟我没关系 - 迭代器模式(Iterator Pattern)

迭代器接口(Iterator):声明了用于遍历集合的方法,如 hasNext() 和 next() 等。具体迭代器必须实现这些方法,以提供特定类型的遍历逻辑。T next();具体迭代器(ConcreteIterator):实现了 Iterator 接口的具体类。聚合接口(Aggregate):接口或抽象类,声明了一个创建迭代器对象的方法。具体聚合类必须实现这个方法,以返回一个与之对应的迭代器实例。Iterator;

2025-01-03 21:45:21 1080 11

原创 电影院售票 - 策略模式(Strategy Pattern)

策略接口(Strategy):定义了所有支持算法公共操作的接口或抽象类。具体策略类必须实现这个接口中的方法。具体策略(ConcreteStrategy):实现了 Strategy 接口的具体类。每个具体策略都提供了一种算法的实现方式。@Override@Override上下文(Context):上下文类拥有一个对策略对象的引用,并提供了设置和获取策略的方法。上下文委托给策略对象来执行具体的算法逻辑。// 设置策略// 执行策略= null) {} else {策略模式的优点。

2025-01-02 21:46:31 1756 3

原创 复杂对象的创建与组装 - 建造者模式(Builder Pattern)

产品(Product): 最终被构建出来的复杂对象。它可以是一个具体的类,也可以是包含多个组件的对象。产品对象并不知道如何创建自己;相反,它依赖于建造者来完成其组装。抽象建造者(Builder):接口或抽象类,声明了用于构建各个组件的方法。具体建造者必须实现这些方法,以提供特定类型的对象构建逻辑。具体建造者(ConcreteBuilder):实现了 Builder 接口的具体类。每个具体建造者都对应一种特定的产品类型,并负责一步一步地构建该产品的不同部分。@Override。

2025-01-01 22:47:13 1567 1

原创 从家谱的层级结构 - 组合模式(Composite Pattern)

定义: 组合多个对象形成树状结构以表示“部分-整体”的层次结构。组合模式让客户端可以一致地使用单个对象和组合。目的: 简化客户端代码对复杂层次结构的操作,同时保持良好的扩展性和灵活性。一致性:客户端可以一致地对待单个对象和组合对象,不需要关心它们的具体类型。灵活性:很容易通过组合模式构建复杂的树形结构,并且可以在不影响现有代码的情况下增加新的组件。符合开闭原则:当需要添加新类型的组件时,只需创建一个新的叶子或组合类,而无需修改现有的代码。

2024-12-28 22:56:56 1136 3

原创 买东西不一定要亲自去,叫个代购也很方便 - 代理模式(Proxy Pattern)

封装变化:可以通过代理对象隐藏真实对象的变化,减少客户端代码与真实对象之间的耦合。增强功能:在不修改真实对象的情况下,通过代理对象添加新的功能,如日志记录、事务管理等。延迟加载:对于大型或复杂对象,可以使用虚拟代理实现延迟加载,提高性能。访问控制:通过保护代理实现细粒度的访问控制,确保只有授权用户才能访问特定资源。代理设计模式是一种非常有用的设计模式,它可以在不修改原始对象的情况下,为其添加额外的功能或控制其访问。然而,在使用时也需要注意其可能带来的复杂性和性能问题。

2024-12-27 22:30:41 1386 1

原创 能省一点是一点 - 享元模式(Flyweight Pattern)

当一个软件需要创建大量的对象的时候,就会导致内存消耗过多,系统性能下降。而享元模式就是为了解决这个问题而出现的设计模式。享元模式(Flyweight Pattern)的核心思想: 如果一个对象实例创建之后不可变的话,反复创建这种实例就变得没有必要,直接向客户端返回一个共享的实例就可以了,这样既节省了内存,还避免了创建对象的过程,提升运行效率。当代码实现中出现大量相同对象的时候,我们就可以考虑使用享元模式。这种设计模式通过共享对象,节约了内存空间,提升了系统性能。减少内存中的对象数量。

2024-12-26 22:42:29 1237 1

原创 有个服务员真好 - 外观模式(Facade Pattern)

外观模式定义与目的定义:为一个复杂的子系统提供一个更简单的接口。目的:简化客户代码对复杂子系统的调用过程,隐藏子系统的内部实现细节。外观模式的角色外观(Facade):提供了简化了的接口给客户端使用。外观类知道如何委托给子系统的各个类,以及如何协调它们的工作。子系统类(Subsystem Classes):每个子系统类都有自己的接口和方法,但它们并不直接暴露给客户端,而是通过外观类来访问。外观模式是一个非常有用的设计模式,特别是在需要简化复杂子系统的使用时。

2024-12-25 21:53:58 920 1

原创 你穿上马甲我还认识你 - 装饰器(Decorator)模式

装饰器(Decorator)模式定义与目的定义:装饰器模式是在不修改原始类文件和使用继承的情况下,动态地扩展一个对象的功能。目的:能够在运行时将责任附加到对象上,提供一种比静态子类化更灵活的解决方案。装饰器(Decorator)模式包含的角色组件(Component): 定义了所有具体组件和装饰器必须实现的操作。它可以是任何可以被装饰的对象。具体组件(ConcreteComponent) : 实现了 Component 接口的具体类,表示被装饰的基本对象。

2024-12-24 19:35:23 1360 8

原创 【只生一个好 - 单例设计模式(Singleton Pattern)】

单例模式的优点唯一性:确保了类在整个应用程序中只有一个实例。控制资源:对于需要严格控制资源使用的场合非常适合。延迟加载:可以通过某些实现方式(如懒汉式、静态内部类)实现延迟初始化,节省资源。线程安全:通过适当的实现方式可以保证在多线程环境下的安全性。单例模式的缺点难以测试:单例模式引入了全局状态,这可能使得单元测试变得困难。隐藏依赖关系:因为单例模式通常通过静态方法提供实例,所以依赖关系往往被隐藏起来,不利于依赖注入和代码维护。

2024-12-23 18:58:55 1591 10

原创 带着国标充电器出国怎么办? 适配器模式(Adapter Pattern)

适配器模式定义与目的定义:适配器模式是一种结构型设计模式,它使接口不兼容的对象能够协作。适配器充当两个不兼容接口之间的桥梁。目的:将一个类的接口转换成客户希望的另一个接口。适配器模式使得原本由于接口不兼容而不能一起工作的那些类可以一起工作。适配器模式的实现方式在Java中,我们主要通过组合或聚合的方式,在适配器内部包含一个对适配者的引用。代码案例// 对象适配器// 构造函数注入适配者@Override适配器模式的过程中一般涉及三个角色:Target 目标。

2024-12-22 22:51:03 1193 3

原创 【Spring框架 四】

Spring 测试框架与 Spring 本身的集成非常紧密,它利用了 Spring 的核心特性如依赖注入(DI)、面向切面编程(AOP)、事务管理等,使得测试更加高效和便捷。

2024-12-22 22:04:03 903 1

原创 跟着我左手右手一个慢动作 —— 模板方法模式

我们通过上面的这个案例,让大家了解了模板方法设计模式。这个模式的核心思想是父类定义主干流程,子类负责细节的实现。同时为了防止子类重写父类的主干流程方法,我们可以把主干流程方法设置为final关键字,这个final关键字用于方法的效果是子类不能更改父类的实现。对final关键字不了解的同学,可以看一下我的这篇文章关键字。对于子类需要实现的抽象方法,我们一般使用protected关键字修饰,这样的话,外部客户端就不可见这些方法了。

2024-12-20 22:06:20 1631 20

原创 还在为什么是面向对象而挠头吗?详解面向对象OOP

面向过程编程和面向对象编程各有优劣,适用于不同类型的应用场景。对于小型、简单的任务,面向过程编程可能是更直接的选择;而对于大型、复杂的系统,尤其是那些需要良好的维护性和扩展性的项目,面向对象编程提供了更强大的工具和支持。在实际开发中,很多现代编程语言都支持多种编程范式,开发者可以根据具体需求选择最合适的风格或混合使用。

2024-12-18 21:11:29 3119 20

原创 【Spring框架 三】

Spring Web 框架概述定义:Spring Web 框架是一个用于开发 Web 应用程序的轻量级框架,它简化了创建复杂的 Web 应用程序的过程。特点:MVC 架构:遵循模型-视图-控制器(MVC)设计模式,使得应用程序的不同方面可以解耦,便于测试和维护。非侵入性:通过依赖注入(DI)和面向接口编程,减少了代码之间的耦合度。灵活性:支持多种视图技术(如 JSP、Thymeleaf、FreeMarker 等),并且可以轻松集成其他第三方库和技术。

2024-12-17 21:16:05 1102

原创 【Java从入门到放弃 之 应用反射实现简单的序列化与反序列化】

上面,我们写了一个简单的序列化与反序列化的案例,让我们体会到反射技术的强大。很明显,通过使用反射,我们的代码会具有更大的灵活性。但是需要注意的是,上面这个简答的序列化与反序列化只是一个让我们体会反射技术的案例,实际上要实现一个序列化与反序列化的通用方法要考虑很多安全性,性能与兼容性的处理。

2024-12-16 21:46:17 504 1

原创 【Java从入门到放弃 之 通用容器类】

Collection 接口概述定义:Collection 是一个代表一组对象(称为元素)的容器的接口。它是所有集合类的顶级接口,但不包括映射(Map)。特点:提供了基本的集合操作方法,如添加、删除、遍历等。不保证元素的顺序,也不保证元素是否唯一(这些特性由具体实现决定)。可以包含重复元素(取决于具体实现),并且允许 null 元素(同样取决于具体实现)List 接口概述定义:List 是一个有序集合,其中每个元素都有一个对应的索引位置。你可以通过索引来访问、插入或删除元素。

2024-12-15 21:00:39 2619 9

原创 【Git教程 之 基本使用】

这一部分,我们主要讲解使用,不带入过多的概念与知识,git一般只是给我们用来管理代码的工具。我们基本的只需要了解工具的使用就好了。如果对git的原理有兴趣,之后我会把自己对git底层原理的理解分享出来。

2024-12-14 14:47:49 330

原创 【Java从入门到放弃 之 HashMap 和 HashSet】

概述定义:HashMap 是一种以哈希表为基础的实现,提供了常数时间复杂度 O(1) 的基本操作(如 get 和 put),假设哈希函数分布均匀。特点:线程不安全:与 Hashtable 不同,HashMap 不是同步的,因此在多线程环境中需要额外的同步机制。允许一个 null 键和多个 null 值:可以包含一个 null 键和任意数量的 null 值。无序:不保证元素的迭代顺序;如果需要有序,可以考虑使用 LinkedHashMap 或 TreeMap。内部工作原理。

2024-12-12 20:40:29 1564 4

原创 【Java从入门到放弃 之 LinkedList 和 ArrayDeque】

概述定义:LinkedList 是一个可以动态调整大小的双向链表实现,允许在列表两端快速添加或移除元素,并且支持按位置插入和删除。特点:线程不安全:与 ArrayList 类似,LinkedList 也不是同步的,多线程环境下需要额外的同步机制。允许重复元素:可以包含多个相同的元素。允许空值:支持存储 null 值,甚至可以存储多个 null。双端队列功能:除了作为普通列表使用外,LinkedList 还提供了双端队列的功能,如在头部或尾部添加/移除元素。内部工作原理。

2024-12-12 15:17:30 1465 1

【Java从入门到放弃 之 从字节码的角度异常处理】文章中的字节码

【Java从入门到放弃 之 从字节码的角度异常处理】文章中的字节码

2024-12-04

空空如也

TA创建的收藏夹 TA关注的收藏夹

TA关注的人

提示
确定要删除当前文章?
取消 删除