leetcode-235.二叉搜索树的最近公共祖先
leetcode-235二叉搜索树的最近公共祖先
原始思路
123456789101112131415161718192021class Solution { public TreeNode lowestCommonAncestor(TreeNode root, TreeNode p, TreeNode q) { return findAncestor(root, p, q); } public static TreeNode findAncestor(TreeNode root, TreeNode p, TreeNode q){ //如果p,q分散在两边,那中间的肯定是共公祖先,当p、q其中一个为root的话,那么必然自己就是祖先 if(p.val > root.val && q.val< root.val || p.val < root.val && q.val> root.val | ...
leetcode-1567.乘积为正数的最长子数组长度
leetcode-1567.乘积为正数的最长子数组长度
原始思路
1234567891011121314151617181920212223242526272829303132333435363738394041424344454647class Solution { public int getMaxLen(int[] nums) { return findMax(nums); } public static int findMax(int[] nums){ //从第一个位置开始,遇到0了就停止并返回最大的数组乘积的起始与结束位置的index Integer max; // 记录此时max为正数的 Integer endIndex; //初始化最大长度为0 int maxLen = 0; for (int i =0; i <nums.length; i++){ endIndex ...
leetcode-98.验证二叉搜索树
leetcode-98.验证二叉搜索树
原始思路:中序排序
123456789101112131415161718192021222324252627282930class Solution { public boolean isValidBST(TreeNode root) { if(root == null){ return true; } AtomicReference<Integer> atomicReference = new AtomicReference<>(); return isValid(root, atomicReference); } // 中序排序遍历,后遍历的树需要大于前一个数 public static boolean isValid(TreeNode current, AtomicReference<Integer> atomicReference){ ...
leetcode-1566.重复至少 K 次且长度为 M 的模式
leetcode-1566.重复至少 K 次且长度为 M 的模式
原始思路实现
123456789101112131415161718192021222324252627282930313233343536373839404142class Solution { public boolean containsPattern(int[] arr, int m, int k) { //边界判断 if(arr.length < m || m<= 0){ return false; } for(int i = 0; i + m -1 < arr.length; i++){ //定义重复次数count int count = 1; //记录找到数组的最后角标 int index = i + m -1; for(int j ...
Spring Cloud
第一:微服务注册中心的注册表如何更好的防止读写并发冲突?
第二:Eureka注册表多级缓存架构有了解过吗?
第三:Nacos如何支撑阿里巴巴内部上百万服务实例的访问?
第四:Nacos高并发异步注册架构知道如何设计的吗?
第五:Sentinel底层滑动时间窗限流算法怎么实现的?
第六:Sentinel底层是如何计算线上系统实时QPS的?
第七:Seata分布式事务回滚机制如何实现的?
第八:Nacos集群CP架构底层类Raft协议怎么实现的?
第九:Nacos&Eureka&Zookeeper集群架构都有脑裂问题吗?
第十:如何设计能支撑全世界公司使用的微服务云架构?
elasticsearch笔记
elasticsearch笔记
RocketMQ笔记 06-事务机制
RocketMQ事务机制
基于half消息的事务机制
生产者如订单系统在发送消息到MQ时,会先发送half消息到MQ,half消息成功后订单系统会收到half发送成功的通知,此时说明MQ存活,订单系统可以执行订单更新等本地事务,如果订单系统的本地事务执行失败可以发送一个rollback请求到MQ,告诉MQ删除之前发的half消息。如果订单系统本地事务执行成功,会发送一个commit请求给MQ进行commit操作,消息被commit之后,消费者才能看见这条消息
如果发送half消息成功了,但是没有收到响应怎么办?
half消息发送给MQ,MQ保存成功,但是由于网络等原因造成订单系统没有收到MQ返回的响应,此时订单系统会误以为发送给MQ失败了,会将订单系统标记为关闭等操作,但是这个时候MQ已经存储了一条half消息,此时由于RocketMQ存在一个补偿机制,MQ会定时扫描自己处于half状态的消息,如果一直没有对这个消息进行commit或者rollback操作,超过一定的时间,就会回调订单系统的接口,让订单系统确认是要commit还是rollback消息,如果订单系统发现 ...
RocketMQ笔记 05-消费者如何拉取消息
消费者如何从Master Broker或者Slaver Broker上拉取数据
ConsumerQueue文件基于os cache
ConsumeQueue会被大量的消费者发送的请求给高并发的读取,所有ConsumeQueue文件的读操作非常频繁,同时也会极大影响消费者进行消息的拉取的性能和消费的吞吐量,所以Broker对ConsumeQueue文件也是基于os cache进行优化,对于Broker大量的ConsumeQueue文件,在写入的时候是优先写入os cache中,而且os也有自己的优化机制,就是在读取一个磁盘文件的时候,会自动把磁盘文件的一些数据缓存到os cache中,由于ConsumeQueue文件主要是存放消息的offset,所以每个文件很小,30万条消息的offset就只有5.72M左右,完全可以被os缓存到内存cache中
CommitLog是基于os cache+磁盘一起读取的
os cache是机器的内存,一般最多也就几十个G而已,对于CommitLog而言,无法将全部数据加载到内存中,os cache主要是提升文件的写入性能,os会自动把旧数据刷 ...
RocketMQ笔记 04-底层原理
底层原理初探
问题概览
生产者往Broker上发送消息的底层原理
Broker接受到消息后是如何储存到磁盘的?
基于DLedger技术部署的Broker高可用集群是如何进行数据同步的?
消费者是基于什么策略选择Master或Slaver拉取数据的?
消费者是如何从Broker拉取数据回来进行处理以及ACK的?如果消费者故障了会怎么办?
数据分片机制及消息是如何发送给Broker?
创建Topic的时候为什么需要指定MessageQueue数量?
MessageQueue是RocketMQ中很重要的一个数据分片机制,它将一个Topic的数据拆分成很多个数据分片,然后在每一个Broker机器上存储一些MessageQueue
生成者发送消息时写入哪个MessageQueue?
生成者在发送消息时首先会去请求NameServer,这样就知道了Topic中有多少个MessageQueue,每个MessageQueue分布在哪个broker上了,这样就可以把一个Topic中的数据分散到多个MessageQueue中,然后分散在多个Broker中
如果某个Broker出现故障了怎 ...
RocketMQ笔记 03-OS内核参数及JVM参数调优
OS内核参数及JVM参数调优
OS内核参数
vm.overcommit_memory
这个参数有0,1,2三个值可选,如果值是0的话,在你的中间件系统申请内存的时候,os内核会检查可用内存是否足够,如果足够的话就分配内存给你,如果感觉剩余内存不是太够了,干脆就拒绝你的申请,导致你申请内存失败,进而导致中间件系统异常出错。
因此一般需要将这个参数的值调整为1,意思是把所有可用的物理内存都允许分配给你,只要有内存就给你来用,这样可以避免申请内存失败的问题,可以用如下命令修改:echo ‘vm.overcommit_memory=1’ >> /etc/sysctl.conf
vm.max_map_count
这个参数的值会影响中间件系统可以开启的线程的数量,同样也是非常重要的,如果这个参数过小,有的时候可能会导致有些中间件无法开启足够的线程,进而导致报错,甚至中间件系统挂掉。他的默认值是65536,但是这个值有时候是不够的,比如我们大数据团队的生产环境部署的Kafka集群曾经有一次就报出过这个异常,说无法开启足够多的线程,直接导致Kafka宕机了。
因此建 ...