<?xml version="1.0" encoding="utf-8" ?><rss version="2.0"><channel><title><![CDATA[Hellyc的博客]]></title><description><![CDATA[]]></description><link>https://blog.youkuaiyun.com/Hellyc</link><language>zh-cn</language><generator>https://blog.youkuaiyun.com/</generator><copyright><![CDATA[Copyright &copy; Hellyc]]></copyright><item><title><![CDATA[使用位图存储发券预约方式、分库分表分析]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149398866</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149398866</guid><author>Hellyc</author><pubDate>Wed, 16 Jul 2025 15:02:35 +0800</pubDate><description><![CDATA[使用jason字符串将所有的预约模式进行存储在预约模式较少的情况下是可行的，但是涉及到序列化与反序列化，这是一部分开销，同时如果预约模式较多，那么需要将jason字符串反序列化为一个list集合，再拿当前传递参数的预约方式遍历的与list集合中的字符串进行对比，这样看来，开销不小。构建主键索引为userID+优惠券ID，因为查询的时候通过用户id与优惠券id就能唯一定义一行数据，并且可能涉及根据用户id查询对应的优惠券信息，所以用户id会放在索引创建的最左侧以满足最左前缀法则。]]></description><category></category></item><item><title><![CDATA[Mysql中存储引擎、索引、sql调优、锁、innodb引擎架构、MVCC多版本并发控制总结]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149370159</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149370159</guid><author>Hellyc</author><pubDate>Tue, 15 Jul 2025 21:46:59 +0800</pubDate><description><![CDATA[行锁是在Mysql中粒度最细的锁，只有innodb引擎支持行级锁，行级锁可以分为行锁、间隙锁、临建锁。innodb引擎通过索引来构建数据内容，行锁只会锁住对于的索引，而不会对数据行row进行加锁。间隙锁会对索引之间的间隙进行加锁，也可以看作是对当前加锁索引的行row的间隙进行加锁，防止对行的间隙进行insert来避免幻读。临建锁是行锁于间隙锁的结合。事务是指一系列的数据库操作需要按照操作顺序原子性的完成，这个过程称为一个事务。]]></description><category></category></item><item><title><![CDATA[八股文——java基础：java枚举类]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149350484</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149350484</guid><author>Hellyc</author><pubDate>Tue, 15 Jul 2025 11:51:06 +0800</pubDate><description><![CDATA[如果想要使用参数，那么就需要使用构造器去初始化参数。并且定义的参数必须使用private final来进行修饰。枚举类就是使用enum修饰的类，这部分类可以只写枚举，也可以为每个枚举添加对应的参数，比如。enum还有对应的enumSet和enumMap。枚举类中也可以有对应的函数方法。]]></description><category></category></item><item><title><![CDATA[redis数据结构和数据类型]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149282549</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149282549</guid><author>Hellyc</author><pubDate>Fri, 11 Jul 2025 20:47:56 +0800</pubDate><description><![CDATA[dict的数据结构包含两张dictht表，记为ht(0)与ht(1)，ht(0)用于存储当前数据，ht(1)用于rehash辅助来扩容与收缩。ht(0)与ht(1)会反复翻转，来实现扩容与收缩。扩容与收缩都是根据负载因子来判断的，最终都会找到离size最近的2^n作为新的存储容量。最后需要了解一个细节，rehash不是一次性转移整张表，而是批量处理部分数据内容，因为数据量大的情况下，处理时间会很长。]]></description><category></category></item><item><title><![CDATA[用户查询优惠券之缓存击穿]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149232290</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149232290</guid><author>Hellyc</author><pubDate>Wed, 09 Jul 2025 19:55:06 +0800</pubDate><description><![CDATA[假设在一个商品秒杀活动场景下，商品ID123正在被秒杀，所有用户访问同一个key：product:123:info，为了减缓高频请求对这一个key的访问，可以将这个热key分片为100个子key，即product:123:info:shard0 ~ product:123:info:shard99，每条子key的内容都是一致的，无论请求访问哪条key的内容，结果都是相同。缓存击穿指的是某个热点key突然失效，比如说过期了，导致大量请求打到缓存，缓存不存在就去访问数据库，导致数据库压力暴增，甚至崩溃。]]></description><category></category></item><item><title><![CDATA[动态规划算法总结（未完）]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149221618</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149221618</guid><author>Hellyc</author><pubDate>Wed, 09 Jul 2025 13:12:08 +0800</pubDate><description><![CDATA[最近在学习回溯和动态规划，感觉都挺头疼的，所以写篇总结合计，方便后续复习。]]></description><category></category></item><item><title><![CDATA[基于模板设计模式开发优惠券推送功能以及对过期优惠卷进行定时清理]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149207672</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149207672</guid><author>Hellyc</author><pubDate>Tue, 08 Jul 2025 22:06:45 +0800</pubDate><description><![CDATA[通过上述DTO可以使得不同功能模块找到自己的实现方式（比如立即发送和延时发送就是通过判别DTO中delayTime是否为null，再比如通过Topic使得不同消费者只监听自己的内容）。通过两个事件类对两个功能模块所需属性做了区分，实质上最终传递的内容就是对应的事件。]]></description><category></category></item><item><title><![CDATA[开发项目时遇到的横向越权、行锁表锁与事务的关联与区别、超卖问题]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149157099</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149157099</guid><author>Hellyc</author><pubDate>Sun, 06 Jul 2025 19:39:08 +0800</pubDate><description><![CDATA[首先需要明确，乐观锁可以是锁，也可以是一种思想。乐观锁的思想是，仅在非读操作的情况下进行检测加锁。也就是” 先不加锁，假设不会发生冲突；在写入前检测是否有冲突，若检测到冲突则重试或报错 “对应的悲观锁思想就是在操作之前进行上锁。比如在解决超卖问题，读写分离时可以新建一个version列：进行读：读出当前version进行写：判断写时的version是否是读时的version，如果不是，则重试或者报错。]]></description><category></category></item><item><title><![CDATA[八股文——JAVA基础：什么是反射？反射的优点和缺点都有哪些？反射的原理是什么？]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149032378</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149032378</guid><author>Hellyc</author><pubDate>Mon, 30 Jun 2025 22:21:25 +0800</pubDate><description><![CDATA[简单来说，反射是一种可以让jvm在动态运行时拿到类的信息的一种方法。在编程时可以通过类对象来获取该类中基本信息，包括类方法、继承关系等。缺点在于安全性不足，因为使用反射可以绕过java的语言限制，比如可以拿到类中private私有的内容。反射的最大优势就在于反射是框架编写的基石，比如使用的spring框架、AOP面向切面编程等都是使用到了反射。反射的优点在于使得代码的编写更加灵活，比如配置文件的加载，只需要在配置文件中进行修改，而不需要修改代码。]]></description><category></category></item><item><title><![CDATA[八股文——什么是泛型？泛型如何使用]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149031808</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149031808</guid><author>Hellyc</author><pubDate>Mon, 30 Jun 2025 21:47:02 +0800</pubDate><description><![CDATA[因为在jdk5版本之前，如List的使用没有泛型，如果添加的过程添加了两个不同类，编译时不会报错，而运行时会出现类转换异常，但是在使用了泛型之后，将报错提前到了编译时期，从而从根本上避免了类转换异常。泛型类比如mybatis plus中的IserviceImpl，通过泛型来标记对应实现类对应的类，泛型接口也可以参考MP中的Iservice，仍然通过泛型来标记对应实现的接口，泛型的应用类别分为泛型类、泛型接口、泛型方法。使用泛型可以增强代码的可读性和稳定性。2.工具类的实现，比如实现不同类的拼接。]]></description><category></category></item><item><title><![CDATA[八股文——JAVA基础：异常处理需要注意哪些]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149031541</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149031541</guid><author>Hellyc</author><pubDate>Mon, 30 Jun 2025 21:08:55 +0800</pubDate><description><![CDATA[其次是明确非受检异常与受检异常，对受检异常进行捕获处理，而非受检异常最好在根源处进行处理，比如逻辑错误就去处理逻辑的错误，而不是进行 异常处理。首先是不要只捕获不处理，这样只是绕过报错，而没有起到真正处理的效果。除此之外，最好适配多个catch块来精准处理捕获的异常。还有就是使用业务自定义异常，调用更加清晰。]]></description><category></category></item><item><title><![CDATA[try-catch-finally 如何使用？]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149030707</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149030707</guid><author>Hellyc</author><pubDate>Mon, 30 Jun 2025 20:27:01 +0800</pubDate><description><![CDATA[try用于捕获代码块的异常，catch用于处理try捕获的可能出现的异常，finally用于善后，比如在try catch中return之前有需要做的事，可以放进finally中。一个try可以有0个到多个catch块，如果没有catch块，那么finally块就必须要有，如果有catch块，finally块是非必须的。finally是否一定会执行？在非极端条件下，finally都会正常执行，除非虚拟机崩溃，线程被杀死finally无法继续执行。finally的一些应用：]]></description><category></category></item><item><title><![CDATA[JAVA八股文：异常有哪些种类，可以举几个例子吗？Throwable类有哪些常见方法？]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/148879444</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/148879444</guid><author>Hellyc</author><pubDate>Mon, 30 Jun 2025 20:04:00 +0800</pubDate><description><![CDATA[Checked 异常通常表示“外部环境或 IO 操作”这类有可能因外部条件（文件不存在、网络中断、权限不足等）而失败的场景。的，Java 通过编译期强制你去“面对”这些错误——要么捕获，要么往上抛，让调用链上的某一层来决定如何恢复或提示用户。（文件、网络、数据库、线程等待等），在这些操作中失败是常态，而不是程序 bug，需要业务层去合理应对。，调用者一眼就能知道“这个方法存在读写失败的风险，需要处理或传递异常”，有助于写出更健壮的程序。出去，让调用者去处理（声明式），要么在方法内部用。]]></description><category></category></item><item><title><![CDATA[八股文——JAVA基础：常量折叠是什么？]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149029929</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149029929</guid><author>Hellyc</author><pubDate>Mon, 30 Jun 2025 19:38:03 +0800</pubDate><description><![CDATA[常量折叠是jvm在底层进行常量的基本运算，比如。]]></description><category></category></item><item><title><![CDATA[八股文——JAVA基础：String s1 = new String(“abc“)；这句话创建了几个字符串对象？]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149004963</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149004963</guid><author>Hellyc</author><pubDate>Sun, 29 Jun 2025 22:34:13 +0800</pubDate><description><![CDATA[需要记住，常量池只会节省字面量（非new出对象时）的内存，因为多个字面量共享同一个常量池内容（常量池实质上是基于哈希表的索引）。如果没有“abc”这个字符串对象，那么会在堆中创建一个对象实例，并且在常量池中创建该实例的索引。如果已有"abc"这个字符串对象，那么常量池中不会再创建，只会在堆中创建一个对象。这段代码创建一个或两个对象。]]></description><category></category></item><item><title><![CDATA[字符串常量池是什么？]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149004784</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149004784</guid><author>Hellyc</author><pubDate>Sun, 29 Jun 2025 22:25:28 +0800</pubDate><description><![CDATA[如果直接使用String s = "hello"，那么hello这个字符串就会被创建在字符串常量池中，如果再创建一个String s2 =  "hello"，那么s与s2拥有相同的地址，因为"hello"是被存放再常量池中的。如果使用new来创建，对应创建的是一个对象，不同对象的地址不同，==比较的是地址，所以两个内容是不同的。这个常量池的思想与Integer的缓存区类似，不但相同。]]></description><category></category></item><item><title><![CDATA[八股文——JAVA基础：字符串拼接用“+” 还是 StringBuilder?]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149004738</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149004738</guid><author>Hellyc</author><pubDate>Sun, 29 Jun 2025 22:12:54 +0800</pubDate><description><![CDATA[操作符 + 底层使用的是StringBuilder来进行实现的，+ 用于拼接的缺陷在于使用StringBuilder，本身线程不安全，其次在循环中使用 + 来拼接，会导致重复创建StringBuilder对象，导致空间的浪费。而在循环中使用StringBuilder就不会出现这个问题。java中仅有两个操作符的重载就是用于字符串的拼接操作的：+与+=]]></description><category></category></item><item><title><![CDATA[String字符串与StringBuffer、StringBuilder的区别以及String的不可变性是什么]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149004362</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149004362</guid><author>Hellyc</author><pubDate>Sun, 29 Jun 2025 22:07:21 +0800</pubDate><description><![CDATA[其中String与StringBuffer是线程安全的，StringBuilder是线程不安全的，因为StringBuilder是直接修改字符串内部，而String与StringBuffer是不会修改内部内容，而是new一个新的对象，并将原来的地址进行覆盖。除此之外，String底层使用private final char[] value来存储字符串，由于使用private，对外部不可见，String内部不提供直接修改的操作，所以外部没法修改，并且使用final关键字，无法修改当前value的值。]]></description><category></category></item><item><title><![CDATA[八股文——JAVA基础：hashCode()方法的作用与意义以及与equals方法的联动]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149003656</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149003656</guid><author>Hellyc</author><pubDate>Sun, 29 Jun 2025 21:15:11 +0800</pubDate><description><![CDATA[但是现在hashcode并不知道，当遇到id相同但内容不同的两个student，hashcode会产生两个不同的散列码，这样就违背了相同的对象的散列码相同的准则。现在有一个类student，student有一个成员变量id，此时equals重写为：id相同时student相同。散列码本身并不能唯一标识对象，不同对象可能会有相同的散列码（即发生哈希冲突）。等基于散列表的数据结构中，当两个对象的 hashCode 相同，会进一步用。在容量不足时，散列表还会触发 rehash，重新分配桶位置以提升性能。]]></description><category></category></item><item><title><![CDATA[深拷贝、浅拷贝、引用拷贝]]></title><link>https://blog.youkuaiyun.com/Hellyc/article/details/149003255</link><guid>https://blog.youkuaiyun.com/Hellyc/article/details/149003255</guid><author>Hellyc</author><pubDate>Sun, 29 Jun 2025 20:36:56 +0800</pubDate><description><![CDATA[首先说浅拷贝，比如现在拷贝一个类的实例，实例中包含成员变量，浅拷贝会重新创建一个地址用于存储该实例，但是现在实例中的成员变量与原本被拷贝的内容拥有同一个成员变量的地址，也就是说两者对于该成员变量是共享的。或者说该成员变量仅仅是被拷贝了地址。引用拷贝相当于构建了个地址的副本，只是为引用地址新开辟了一个空间。而深拷贝是将所有的内容都进行了重建，与拷贝的内容完全隔离开的。]]></description><category></category></item></channel></rss>