赛题一:找出各项考试中的佼佼者
解题思路
1、分数去重
一个学生可以参加任意考试,不限次数。
若同一个考生有多条考试记录,则取最高分。
根据上述题意,在分数 testattempt 表中按照考试类型获取每个学生的最高分数,以此来保证每个学生在每门考试中只存在一个最高分。由此,我们得到第一个子表 t 。
select`score`) , (`studentId`, `testId``testattempt``studentId`, `testId`
2、进行分类排序
找出每个考试中 得分最高的的考生 。
如果存在并列,将并列的考生都列举出来,直到列举的考生达到或超过三人。
- 先对第一步表中的数据按照考试类型将分数从高到低排序,因此使用 order by t.testid,t.score desc ;
- 根据同考试类型对分数进行排名,也就是相同的分数也排名相同。这里有两种方法,一种是我们可借助变量赋值的方式进行排名处理,另一种是借助于窗口函数 DENSE_RANK() 来处理。(代码参考后续截图代码)
3、根据排名取出前三
基于第二步的排名通过判断排名小于等于3来筛选出前三的学生,为方便显示,可再进行一次分数排序
方法一
.`name` , .`name` , . ( *, .-- 排名代码,如果考试 与上一个不同,那么排名从1开始 @rank := ( @prev_test=`testid`, -- 如果分数 与上一个相同则沿用上次的排名,否则排名+1@score=.@rank@score :=.@rank :=@rank+1END, 1 ) `rank`, @score :=. , @prev_test :=`testid` ( select`score`) , (`studentId`, `testId``testattempt``studentId`, `testId` ) .`testid`, .`score` ) `test`.=.`id`join`student`.=`student`.`id`.<=3. , .
方法二
.`name` , .`name` , . ( *, .-- 此处使用 () 进行不跳号排序 (`testId`. )) () ( ( select`score`) , (`studentId`, `testId``testattempt``studentId`, `testId` ) ) `test`.=.`id`join`student`.=`student`.`id`.<=3. , .
赛题二:游戏游玩情况
解题思路
1、计算总用户数
因用户可在不同日期登录,所以在数据表中存在多条记录因此需要按照 player_id 做去重后在计算用户数
`player_id`)) ( (`activity`
2、获取用户首次登录后7天的日期范围
按照用户 player_id 做分组,取最小的登录日期,使用 date_add 计算该日期7天内的日期,或者通过使用datediff结合变量赋值计算出距离第一次登陆时间时间差,从而得到中间表(方法一的 t2 ,方法二的 t1)。
PS:因为本题中给定的时间是日期格式,所以如果需求不算登录当天的话,date_add 的数值应该为 6。比如:5月24日的7天内的截止日期为 5月30日,而不是 5月31日。本题结果使用7做计算。
3、获取首次登录7天后登录的用户数量
使用 activity 表与步骤2中的 t2 做 join 查询,设置activity 表中的登录时间在 t2 的区间范围内,利用 group by player_id having count(1) >1,由此得到满足条件的用户。再对结果集进行 count 即可得到首次登录后7天后的登录用户数量
4、计算百分比并四舍五入保留两位小数
使用 round() 函数对步骤3中的数据除以步骤1中的数据,得到四舍五入的结果。
方法一
( . ) / ( (`player_id`)) ( (`activity` ), 2 ) ( .`player_id`, 1) (`activity`join ( ( ) , 7 ) , ( ( ), `player_id``activity``player_id` ) .`player_id`=..`event_date`.and..`player_id`1) >1 ( )
方法二
select ( ./ ( `player_id`)) ( (`activity` ), 2 ) ( `player_id`)) ( ( ( `player_id`, `event_date`, when@player_id=`player_id` (`event_date`, @prev_date) when@player_id :=`player_id`0 , when@player_id1=`player_id`@prev_datewhen@player_id1 :=`player_id`@prev_date :=`event_date``activity``player_id`, `event_date` ) .<=7and.>0 )
赛题三:计算三角形面积
解题思路
1、确认三角形计算面积公式
此处使用向量叉积的方式计算三角形面积。假设三个点坐标如下 (x1,y1,z1),(x2,y2,z2),(x3,y3,z3),那么该三角形组成的面积S的公式为:
2、获取三个点的具体坐标值
使用 join 方法分别将 triangle 表中三个点的具体坐标值,然后再使用公式计算即可。这里我们会需要用到求平方的函数 pow,以及求平方根的函数 sqrt。
结果
. , ( sqrt( - ), 2) * ((- ), 2) + ((- ), 2) * ((- ), 2) + ((- ), 2) * ((- ), 2) (( ) *0.5, 2 ) ( . , .`x` , .`y` , .`z` , .`x` , .`y` , .`z` , .`x` , .`y` , .`z``triangle`join`point`.`pointId1`=.`id`join`point`.`pointId2`=.`id`join`point`.`pointId3`=.`id` )