- 为了助力本届青训营课程的学习,青训营项目组为同学们精心挑选了练手习题 📖
- 每两天发布一篇,包含选择题和实操题各一题(第二天将发布答案解析)🥳
- 同学们可以在评论区留下你的解题过程并进行互动交流 ✍️
一、【单选】使用 SQL 语句进行分组检索时,为了去掉不满足条件的分组,应当:
a. 使用 WHERE 子句
b. 在 GROUPBY 后面使用 HAVING 子句
c. 先使用 WHERE 子句,再使用 HAVING 子句
d. 先使用 HAVING 子句,再使用 WHERE 子句
答案 & 解析
c;
having 是对分组统计结果进行筛选,where 是对基础数据进行筛选。
为什么没有选 b: 这个与sql执行过程有关,where 在最开始发挥作用,having对group by之后的结果发挥作用,所以选择尽量前置,降低group by等阶段的操作数据量。 b 的意思是把where的选择放到having里,所以相当于所有选择都后置了。 注意理解题意哟。
二、实现一个 key 为字符串,value 也是字符串的,而且并发安全的 map,拥有方法 set(key string, value string)、get(key string) string、del(key string)。
扩展要求1: 字典初始有64个桶,当有一半以上的队列有多个元素时,进行自动扩容,将桶的数量翻倍。
扩展要求2: 当一半以上的队列都为空或只有一个元素,并且这种情况持续1分钟,则自动缩容,最小缩容到64队列。
解析
为了满足基础要求,可以实现一个hash map,并且加一个大锁(读写锁或者互斥锁都可以)即可实现;更近一步,可以考虑为每个桶加一把独立的锁,可以实现更小粒度的锁。接下来可以使用go test的banchmark能力去测试下不同读写压力、不同锁粒度、不同类型的锁下的性能对比。
如果为了实现字典的自动扩缩容,则需要实现两个hash map,一个是current hash map,另一个是next hash map。在每次读写中,将current hash map中的几个key迁移到next hash map。在读操作中,先找current hash map,如果key不存在,再找next hash map;在写操作中,会先删除current hash map中这个key,再写入next hash map。随着不断的读写,则会慢慢current hash map会为空,此时将next hash map改成current hash map即可。
这里有几个难点 :
- 如何去遍历current hash map,来做迁移?
需要记录上次遍历到的桶和key,以便于下次继续遍历
- 如何判断current hash map已经为空了?
记录一下map中key的个数,如果为0了,则说明为空了。可以使用atomic这个库来实现。
- 如何判断需要扩容 / 缩容?
也记录一下不为空的桶的数量。
今天是第五天打卡,同学们加油~