最细哈希表相关的力扣题和讲解和Java、C++常用的数据结构(哈希法)来源于代码随想录,十分感谢这位我失散多年的老师!!

20240725

  • 一、什么时候适用什么样的结构。
    • 1.java中
      • [1.1 HashSet:](#1.1 HashSet:)
      • [1.2 TreeSet:](#1.2 TreeSet:)
      • [1.3 LinkedHashSet:](#1.3 LinkedHashSet:)
      • [1.4 HashMap:](#1.4 HashMap:)
      • [1.5 TreeMap:](#1.5 TreeMap:)
      • [1.6 LinkedHashMap:](#1.6 LinkedHashMap:)
      • [1.7 总结](#1.7 总结)
    • [2. c++中](#2. c++中)
      • [2.1 std::unordered_set:](#2.1 std::unordered_set:)
      • [2.2 std::set:](#2.2 std::set:)
      • [2.3 std::multiset:](#2.3 std::multiset:)
      • [2.4 std::unordered_map:](#2.4 std::unordered_map:)
      • [2.5 std::map:](#2.5 std::map:)
      • [2.6 std::multimap:](#2.6 std::multimap:)
    • [3 代码随想录中对与哈希法的总结](#3 代码随想录中对与哈希法的总结)
  • 二、题目和讲解
    • [1 用数组](#1 用数组)
      • [242. 有效的字母异位词](#242. 有效的字母异位词)
      • [383. 赎金信](#383. 赎金信)
    • [2. 用set的题](#2. 用set的题)
      • [349. 两个数组的交集](#349. 两个数组的交集)
    • [350. 两个数组的交集 II(对于给定范围了,而且重复的,先考虑数组,因为会快很多)](#350. 两个数组的交集 II(对于给定范围了,而且重复的,先考虑数组,因为会快很多))
    • [1 两数之和(hashmap)](#1 两数之和(hashmap))
    • [454 四数相加](#454 四数相加)
    • [第15题. 三数之和](#第15题. 三数之和)
      • [Java:(版本一) 双指针(建议)](#Java:(版本一) 双指针(建议))
      • [(版本二) 使用哈希集合](#(版本二) 使用哈希集合)
    • [第18题. 四数之和](#第18题. 四数之和)
  • 三、总结

(来源于代码随想录,十分感谢这位我失散多年的老师!!!)

一、什么时候适用什么样的结构。

1.java中

Java 中的数据结构及其使用场景

1.1 HashSet:

底层实现:哈希表。

特点:无序集合,元素唯一。

使用场景:

需要快速查找、插入和删除操作,并且不关心元素的顺序。

适合于需要去重的集合,例如存储唯一的用户ID或配置项。

1.2 TreeSet:

底层实现:红黑树。

特点:有序集合,元素唯一,按自然顺序或指定的比较器排序。

使用场景:

需要保持元素的排序,并且需要高效的顺序相关操作(如范围查询)。

适合于需要有序集合的应用场景,例如任务调度系统或有序数据处理。

1.3 LinkedHashSet:

底层实现:哈希表和双向链表。

特点:保持插入顺序的无序集合,元素唯一。

使用场景:

需要保持元素的插入顺序,并且需要高效的查找、插入和删除操作。

适合于需要插入顺序的集合,如实现缓存机制或历史记录功能。

1.4 HashMap:

底层实现:哈希表。

特点:无序的键值对集合,键唯一,值可以重复。

使用场景:

需要高效的键值对查找、插入和删除操作,不关心键值对的顺序。

适合于实现字典、缓存、配置管理等场景。

1.5 TreeMap:

底层实现:红黑树。

特点:有序的键值对集合,键唯一,按键的自然顺序或指定的比较器排序。

使用场景:

需要保持键的有序性,并进行高效的范围查询操作。

适合于需要按键排序的场景,例如实现排序的配置项存储或基于键的范围查询。

1.6 LinkedHashMap:

底层实现:哈希表和双向链表。

特点:保持插入顺序的键值对集合,键唯一。

使用场景:

需要保持插入顺序,并且需要高效的键值对查找、插入和删除操作。

适合于实现有序缓存(如最近最少使用缓存)或需要记录插入顺序的映射。

1.7 总结

HashSet 和 HashMap 提供了基于哈希的高效查找和操作,适合不关心顺序的场景。

TreeSet 和 TreeMap 提供了基于红黑树的有序操作,适合需要排序和范围查询的场景。

LinkedHashSet 和 LinkedHashMap 提供了保持插入顺序的功能,适合需要记录元素插入顺序的场景。

2. c++中

2.1 std::unordered_set:

底层实现:哈希表。

特点:无序集合,提供常数时间复杂度的平均增、删、查操作。

适用场景:当需要高效的查找操作,并且元素的顺序无关紧要时使用。

2.2 std::set:

底层实现:红黑树(平衡二叉搜索树)。

特点:有序集合,元素按照一定顺序存储,提供对数时间复杂度的增、删、查操作。

适用场景:当需要有序集合,且集合中不允许重复元素时使用。

2.3 std::multiset:

底层实现:红黑树(平衡二叉搜索树)。

特点:有序集合,允许重复元素。

适用场景:当需要有序集合,并且允许重复元素时使用。

2.4 std::unordered_map:

底层实现:哈希表。

特点:无序的键值对集合,提供常数时间复杂度的平均增、删、查操作。

适用场景:当需要高效的键值对查找,且键值对的顺序无关紧要时使用。

2.5 std::map:

底层实现:红黑树(平衡二叉搜索树)。

特点:有序的键值对集合,键是唯一的,提供对数时间复杂度的增、删、查操作。

适用场景:当需要有序的键值对集合,并且键值对的顺序是重要的时使用。

2.6 std::multimap:

底层实现:红黑树(平衡二叉搜索树)。

特点:有序的键值对集合,键允许重复,提供对数时间复杂度的增、删、查操作。

适用场景:当需要有序的键值对集合,并且允许键重复时使用。

3 代码随想录中对与哈希法的总结


二、题目和讲解

1 用数组

242. 有效的字母异位词

给定两个字符串 s 和 t ,编写一个函数来判断 t 是否是 s 的字母异位词。

注意:若 s 和 t 中每个字符出现的次数都相同,则称 s 和 t 互为字母异位词。

bash 复制代码
/**
 * 242. 有效的字母异位词 字典解法
 * 时间复杂度O(m+n) 空间复杂度O(1)
 */
class Solution {
    public boolean isAnagram(String s, String t) {
        int[] record = new int[26];

        for (int i = 0; i < s.length(); i++) {
            record[s.charAt(i) - 'a']++;     // 并不需要记住字符a的ASCII,只要求出一个相对数值就可以了
        }

        for (int i = 0; i < t.length(); i++) {
            record[t.charAt(i) - 'a']--;
        }
        
        for (int count: record) {
            if (count != 0) {               // record数组如果有的元素不为零0,说明字符串s和t 一定是谁多了字符或者谁少了字符。
                return false;
            }
        }
        return true;                        // record数组所有元素都为零0,说明字符串s和t是字母异位词
    }
}

383. 赎金信

给你两个字符串:ransomNote 和 magazine ,判断 ransomNote 能不能由 magazine 里面的字符构成。

如果可以,返回 true ;否则返回 false 。

magazine 中的每个字符只能在 ransomNote 中使用一次。

bash 复制代码
class Solution {
    public boolean canConstruct(String ransomNote, String magazine) {
            int[] arr=new int[26];
            for(int i=0;i<magazine.length();++i){
                arr[magazine.charAt(i)-'a']++;
            }
            for(int i=0;i<ransomNote.length();++i){
                arr[ransomNote.charAt(i)-'a']--;
            }
            for(int a:arr){
                if(a<0){
                    return false;
                }
            }
            return true;
    }
}

2. 用set的题

349. 两个数组的交集

给定两个数组 nums1 和 nums2 ,返回 它们的

交集

输出结果中的每个元素一定是 唯一 的。我们可以 不考虑输出结果的顺序 。

示例 1:

输入:nums1 = [1,2,2,1], nums2 = [2,2]

输出:[2]

示例 2:

bash 复制代码
使用HashSet

import java.util.HashSet;
import java.util.Set;

class Solution {
    public int[] intersection(int[] nums1, int[] nums2) {
        if (nums1 == null || nums1.length == 0 || nums2 == null || nums2.length == 0) {
            return new int[0];
        }
        Set<Integer> set1 = new HashSet<>();
        Set<Integer> resSet = new HashSet<>();
        //遍历数组1
        for (int i : nums1) {
            set1.add(i);
        }
        //遍历数组2的过程中判断哈希表中是否存在该元素
        for (int i : nums2) {
            if (set1.contains(i)) {
                resSet.add(i);
            }
        }
      
        //方法1:将结果集合转为数组

        return resSet.stream().mapToInt(x -> x).toArray();
        
        //方法2:另外申请一个数组存放setRes中的元素,最后返回数组
        int[] arr = new int[resSet.size()];
        int j = 0;
        for(int i : resSet){
            arr[j++] = i;
        }
        
        return arr;
    }
}
bash 复制代码
使用Hash数组

class Solution {
    public int[] intersection(int[] nums1, int[] nums2) {
        int[] hash1 = new int[1002];
        int[] hash2 = new int[1002];
        for(int i : nums1)//将nums1出现的数字次数进行存储
            hash1[i]++;
        for(int i : nums2)
            hash2[i]++;
        List<Integer> resList = new ArrayList<>();
        for(int i = 0; i < 1002; i++)
            if(hash1[i] > 0 && hash2[i] > 0)//如果i都大于0,证明都都存在,所以直接添加到List集合。
                resList.add(i);
        int index = 0;
        int res[] = new int[resList.size()];
        for(int i : resList)//返回数组,所以转为数组
            res[index++] = i;
        return res;
    }
}

350. 两个数组的交集 II(对于给定范围了,而且重复的,先考虑数组,因为会快很多)

给你两个整数数组 nums1 和 nums2 ,请你以数组形式返回两数组的交集。返回结果中每个元素出现的次数,应与元素在两个数组中都出现的次数一致(如果出现次数不一致,则考虑取较小值)。可以不考虑输出结果的顺序。

示例 1:

输入:nums1 = [1,2,2,1], nums2 = [2,2]

输出:[2,2]

数组

bash 复制代码
class Solution {
    public int[] intersect(int[] nums1, int[] nums2) {
        int[] counter1 = new int[1001];
        int[] counter2 = new int[1001];

        for (int num : nums1) {
            counter1[num]++;
        }

        int index = 0;
        for (int num : nums2) {
            if (counter1[num] > 0) {
                counter1[num]--;
                counter2[index] = num;
                index++;
            }
        }

        return Arrays.copyOfRange(counter2, 0, index);
    }
}

HashMap

bash 复制代码
class Solution {
    public int[] intersect(int[] nums1, int[] nums2) {
         if (nums1 == null || nums1.length == 0 || nums2 == null || nums2.length == 0) {
            return new int[0];
        }
       
        HashMap<Integer, Integer> map = new HashMap<>();
        List<Integer> resultList = new ArrayList<>();
        
        // 记录 nums1 中每个元素的出现次数
        for (int num : nums1) {
            map.put(num, map.getOrDefault(num, 0) + 1);
        }

        // 遍历 nums2,检查元素是否在 map 中,并更新结果
        for (int num : nums2) {
            if (map.containsKey(num) && map.get(num) > 0) {
                resultList.add(num);
                map.put(num, map.get(num) - 1);
            }
        }

        // 将结果 List 转换为数组
        return resultList.stream().mapToInt(i -> i).toArray();

    }

}

1 两数之和(hashmap)

给定一个整数数组 nums 和一个整数目标值 target,请你在该数组中找出 和为目标值 target 的那 两个 整数,并返回它们的数组下标。

你可以假设每种输入只会对应一个答案。但是,数组中同一个元素在答案里不能重复出现。

你可以按任意顺序返回答案。

bash 复制代码
class Solution {
    public int[] twoSum(int[] nums, int target) {
        int[] arr=new int[2];//因为返回一个就好了,所以我们定义一个两个长度的数组
        if(nums.length==0||nums==null){//首先先判断这个不满足条件
            return arr;//然后这个空
        }
        Map<Integer,Integer> result=new HashMap<>();//定义一个合适的map,这里适合用hashmap,快速查找
        for(int i=0;i<nums.length;i++){
            int temp=target-nums[i];//用来判断和这个数组合等于target的数
            if(result.containsKey(temp)){//判断这个数是否在map里
                arr[0]=result.get(temp);//因为我们是把值当作key,把索引当成value,所以通过temp拿到索引
                arr[1]=i;
            }
            result.put(nums[i], i);//存入值和索引
        }
return arr;
    }
}

双指针法

bash 复制代码
//使用双指针
public int[] twoSum(int[] nums, int target) {
    int m=0,n=0,k,board=0;
    int[] res=new int[2];
    int[] tmp1=new int[nums.length];
    //备份原本下标的nums数组
    System.arraycopy(nums,0,tmp1,0,nums.length);
    //将nums排序
    Arrays.sort(nums);
    //双指针
    for(int i=0,j=nums.length-1;i<j;){
        if(nums[i]+nums[j]<target)
            i++;
        else if(nums[i]+nums[j]>target)
            j--;
        else if(nums[i]+nums[j]==target){
            m=i;
            n=j;
            break;
        }
    }
    //找到nums[m]在tmp1数组中的下标
    for(k=0;k<nums.length;k++){
        if(tmp1[k]==nums[m]){
            res[0]=k;
            break;
        }
    }
    //找到nums[n]在tmp1数组中的下标
    for(int i=0;i<nums.length;i++){
        if(tmp1[i]==nums[n]&&i!=k)
            res[1]=i;
    }
    return res;
}

454 四数相加

bash 复制代码
class Solution {
    public int fourSumCount(int[] nums1, int[] nums2, int[] nums3, int[] nums4) {
        int res = 0;
        Map<Integer, Integer> map = new HashMap<Integer, Integer>();
        //统计两个数组中的元素之和,同时统计出现的次数,放入map
        for (int i : nums1) {
            for (int j : nums2) {
                int sum = i + j;//求出第一个数组和第二个数组的和
                map.put(sum, map.getOrDefault(sum, 0) + 1);//getOrDefault这个的意思是,如果存在,返回存在的值,不存在返回default0
            }
        }
        //统计剩余的两个元素的和,在map中找是否存在相加为0的情况,同时记录次数
        for (int i : nums3) {
            for (int j : nums4) {
                res += map.getOrDefault(0 - i - j, 0);//0-(i+j)如果找到了,就加上0 - i - j的velu,找不到+0
            }
        }
        return res;
    }
}

第15题. 三数之和

力扣题目链接(opens new window)

给你一个包含 n 个整数的数组 nums,判断 nums 中是否存在三个元素 a,b,c ,使得 a + b + c = 0 ?请你找出所有满足条件且不重复的三元组。

注意: 答案中不可以包含重复的三元组。

示例:

给定数组 nums = [-1, 0, 1, 2, -1, -4],

满足要求的三元组集合为: [ [-1, 0, 1], [-1, -1, 2]

Java:(版本一) 双指针(建议)

bash 复制代码
class Solution {
    public List<List<Integer>> threeSum(int[] nums) {
        List<List<Integer>> result = new ArrayList<>();
        Arrays.sort(nums);
	// 找出a + b + c = 0
        // a = nums[i], b = nums[left], c = nums[right]
        for (int i = 0; i < nums.length; i++) {
	    // 排序之后如果第一个元素已经大于零,那么无论如何组合都不可能凑成三元组,直接返回结果就可以了
            if (nums[i] > 0) { 
                return result;
            }

            if (i > 0 && nums[i] == nums[i - 1]) {  // 去重a
                continue;
            }

            int left = i + 1;
            int right = nums.length - 1;
            while (right > left) {
                int sum = nums[i] + nums[left] + nums[right];
                if (sum > 0) {
                    right--;
                } else if (sum < 0) {
                    left++;
                } else {
                    result.add(Arrays.asList(nums[i], nums[left], nums[right]));
		    // 去重逻辑应该放在找到一个三元组之后,对b 和 c去重
                    while (right > left && nums[right] == nums[right - 1]) right--;
                    while (right > left && nums[left] == nums[left + 1]) left++;
                    
                    right--; 
                    left++;
                }
            }
        }
        return result;
    }
}

(版本二) 使用哈希集合

bash 复制代码
class Solution {
    public List<List<Integer>> threeSum(int[] nums) {
	List<List<Integer>> result = new ArrayList<>();
	Arrays.sort(nums);

	for (int i = 0; i < nums.length; i++) {
		// 如果第一个元素大于零,不可能凑成三元组
		if (nums[i] > 0) {
			return result;
		}
		// 三元组元素a去重
		if (i > 0 && nums[i] == nums[i - 1]) {
			continue;
		}

		HashSet<Integer> set = new HashSet<>();
		for (int j = i + 1; j < nums.length; j++) {
			// 三元组元素b去重
			if (j > i + 2 && nums[j] == nums[j - 1] && nums[j - 1] == nums[j - 2]) {
				continue;
			}

			int c = -nums[i] - nums[j];
			if (set.contains(c)) {
				result.add(Arrays.asList(nums[i], nums[j], c));
				set.remove(c); // 三元组元素c去重
			} else {
				set.add(nums[j]);
			}
		}
	}
	return result;
    }
}

第18题. 四数之和

力扣题目链接(opens new window)

题意:给定一个包含 n 个整数的数组 nums 和一个目标值 target,判断 nums 中是否存在四个元素 a,b,c 和 d ,使得 a + b + c + d 的值与 target 相等?找出所有满足条件且不重复的四元组。

注意:

答案中不可以包含重复的四元组。

示例: 给定数组 nums = [1, 0, -1, 0, -2, 2],和 target = 0。 满足要求的四元组集合为: [ [-1, 0, 0, 1], [-2, -1, 1, 2], [-2, 0, 0, 2] ]

bash 复制代码
class Solution {
    public List<List<Integer>> fourSum(int[] nums, int target) {
        List<List<Integer>> result = new ArrayList<>();
        Arrays.sort(nums);
       
        for (int i = 0; i < nums.length; i++) {
		
            // nums[i] > target 直接返回, 剪枝操作
            if (nums[i] > 0 && nums[i] > target) {
                return result;
            }
		
            if (i > 0 && nums[i - 1] == nums[i]) {    // 对nums[i]去重
                continue;
            }
            
            for (int j = i + 1; j < nums.length; j++) {

                if (j > i + 1 && nums[j - 1] == nums[j]) {  // 对nums[j]去重
                    continue;
                }

                int left = j + 1;
                int right = nums.length - 1;
                while (right > left) {
		    // nums[k] + nums[i] + nums[left] + nums[right] > target int会溢出
                    long sum = (long) nums[i] + nums[j] + nums[left] + nums[right];
                    if (sum > target) {
                        right--;
                    } else if (sum < target) {
                        left++;
                    } else {
                        result.add(Arrays.asList(nums[i], nums[j], nums[left], nums[right]));
                        // 对nums[left]和nums[right]去重
                        while (right > left && nums[right] == nums[right - 1]) right--;
                        while (right > left && nums[left] == nums[left + 1]) left++;

                        left++;
                        right--;
                    }
                }
            }
        }
        return result;
    }
}

三、总结

哈希表总结篇

哈希表理论基础

在关于哈希表,你该了解这些! (opens new window)中,我们介绍了哈希表的基础理论知识,不同于枯燥的讲解,这里介绍了都是对刷题有帮助的理论知识点。

一般来说哈希表都是用来快速判断一个元素是否出现集合里。

对于哈希表,要知道哈希函数和哈希碰撞在哈希表中的作用。

哈希函数是把传入的key映射到符号表的索引上。

哈希碰撞处理有多个key映射到相同索引上时的情景,处理碰撞的普遍方式是拉链法和线性探测法。

接下来是常见的三种哈希结构:

数组

set(集合)

map(映射)

在C++语言中,set 和 map 都分别提供了三种数据结构,每种数据结构的底层实现和用途都有所不同,在关于哈希表,你该了解这些! (opens new window)中我给出了详细分析,这一知识点很重要!

例如什么时候用std::set,什么时候用std::multiset,什么时候用std::unordered_set,都是很有考究的。

只有对这些数据结构的底层实现很熟悉,才能灵活使用,否则很容易写出效率低下的程序。

哈希表经典题目

数组作为哈希表

一些应用场景就是为数组量身定做的。

在242.有效的字母异位词 (opens new window)中,我们提到了数组就是简单的哈希表,但是数组的大小是受限的!

这道题目包含小写字母,那么使用数组来做哈希最合适不过。

在383.赎金信 (opens new window)中同样要求只有小写字母,那么就给我们浓浓的暗示,用数组!

本题和242.有效的字母异位词 (opens new window)很像,242.有效的字母异位词 (opens new window)是求 字符串a 和 字符串b 是否可以相互组成,在383.赎金信 (opens new window)中是求字符串a能否组成字符串b,而不用管字符串b 能不能组成字符串a。

一些同学可能想,用数组干啥,都用map不就完事了。

上面两道题目用map确实可以,但使用map的空间消耗要比数组大一些,因为map要维护红黑树或者符号表,而且还要做哈希函数的运算。所以数组更加简单直接有效!

#set作为哈希表

在349. 两个数组的交集 (opens new window)中我们给出了什么时候用数组就不行了,需要用set。

这道题目没有限制数值的大小,就无法使用数组来做哈希表了。

主要因为如下两点:

数组的大小是有限的,受到系统栈空间(不是数据结构的栈)的限制。

如果数组空间够大,但哈希值比较少、特别分散、跨度非常大,使用数组就造成空间的极大浪费。

所以此时一样的做映射的话,就可以使用set了。

关于set,C++ 给提供了如下三种可用的数据结构:(详情请看关于哈希表,你该了解这些! (opens new window))

std::set

std::multiset

std::unordered_set

std::set和std::multiset底层实现都是红黑树,std::unordered_set的底层实现是哈希, 使用unordered_set 读写效率是最高的,本题并不需要对数据进行排序,而且还不要让数据重复,所以选择unordered_set。

在202.快乐数 (opens new window)中,我们再次使用了unordered_set来判断一个数是否重复出现过。

map作为哈希表

在1.两数之和 (opens new window)中map正式登场。

来说一说:使用数组和set来做哈希法的局限。

数组的大小是受限制的,而且如果元素很少,而哈希值太大会造成内存空间的浪费。

set是一个集合,里面放的元素只能是一个key,而两数之和这道题目,不仅要判断y是否存在而且还要记录y的下标位置,因为要返回x 和 y的下标。所以set 也不能用。

map是一种<key, value>的结构,本题可以用key保存数值,用value在保存数值所在的下标。所以使用map最为合适。

C++提供如下三种map:(详情请看关于哈希表,你该了解这些! (opens new window))

std::map

std::multimap

std::unordered_map

std::unordered_map 底层实现为哈希,std::map 和std::multimap 的底层实现是红黑树。

同理,std::map 和std::multimap 的key也是有序的(这个问题也经常作为面试题,考察对语言容器底层的理解),1.两数之和 (opens new window)中并不需要key有序,选择std::unordered_map 效率更高!

在454.四数相加 (opens new window)中我们提到了其实需要哈希的地方都能找到map的身影。

本题咋眼一看好像和18. 四数之和 (opens new window),15.三数之和 (opens new window)差不多,其实差很多!

关键差别是本题为四个独立的数组,只要找到A[i] + B[j] + C[k] + D[l] = 0就可以,不用考虑重复问题,而18. 四数之和 (opens new window),15.三数之和 (opens new window)是一个数组(集合)里找到和为0的组合,可就难很多了!

用哈希法解决了两数之和,很多同学会感觉用哈希法也可以解决三数之和,四数之和。

其实是可以解决,但是非常麻烦,需要去重导致代码效率很低。

在15.三数之和 (opens new window)中我给出了哈希法和双指针两个解法,大家就可以体会到,使用哈希法还是比较麻烦的。

所以18. 四数之和,15.三数之和都推荐使用双指针法!

总结

对于哈希表的知识相信很多同学都知道,但是没有成体系。

本篇我们从哈希表的理论基础到数组、set和map的经典应用,把哈希表的整个全貌完整的呈现给大家。

同时也强调虽然map是万能的,详细介绍了什么时候用数组,什么时候用set。

相信通过这个总结篇,大家可以对哈希表有一个全面的了解。

相关推荐
摇滚侠6 分钟前
Spring Boot3零基础教程,SpringApplication 自定义 banner,笔记54
java·spring boot·笔记
青云交9 分钟前
Java 大视界 -- Java 大数据机器学习模型在游戏用户行为分析与游戏平衡优化中的应用
java·大数据·机器学习·数据存储·模型构建·游戏用户行为分析·游戏平衡优化
循着风1 小时前
二叉树的多种遍历方式
数据结构·算法
暗武逢天3 小时前
Java导出写入固定Excel模板数据
java·导出数据·easyexcel·excel固定模板导出
摇滚侠3 小时前
Spring Boot3零基础教程,KafkaTemplate 发送消息,笔记77
java·spring boot·笔记·后端·kafka
fat house cat_6 小时前
【netty】基于主从Reactor多线程模型|如何解决粘包拆包问题|零拷贝
java·服务器·网络·netty
.格子衫.6 小时前
022数据结构之树状数组——算法备赛
数据结构·算法·1024程序员节
Yupureki6 小时前
从零开始的C++学习生活 16:C++11新特性全解析
c语言·数据结构·c++·学习·visual studio
青云交6 小时前
Java 大视界 -- Java 大数据在智能教育学习社区互动模式创新与用户活跃度提升中的应用(426)
java·大数据·学习·flink 实时计算·智能教育社区·互动模式创新·用户活跃度
神奇的海马体7 小时前
Tomcat隐藏版本号
java·tomcat