leetcode database problem sixth bullet

626. Change seats

https://leetcode.cn/problems/exchange-seats/

Well, I looked at this topic again today and found that the use case has been fixed.

# mysql && oracle
select floor((id - 1) / 2) * 2 + row_number() over(partition by floor((id - 1) / 2) order by id desc) id ,student
from seat
# mssql
select (id - 1) / 2 * 2 + row_number() over(partition by (id - 1) / 2 order by id desc) id ,student
from seat
# mssql && mysql
# 这个是抄评论里的内容,可惜不直到怎么调整的能够支持 oracle
select rank() over (order by (id - 1) ^ 1) id, student
from Seat

1280. Number of times students took tests in each subject

https://leetcode.cn/problems/students-and-examinations/

Forehead. . . Count everyone, all subjects, and several assessments have been carried out. . . Then personnel and subjects can only maximize the cross-query, and then associate the number of exams.

In fact, the instructions are one for three, just replace the null value processing with their own functions:

oracle : nvl
mysql : ifnull
mssql : isnull

# oracle
select a.*,nvl(cnt,0) attended_exams 
from (
    select * from students,subjects
) a
left join (
    select student_id,subject_name,count(0) cnt
    from examinations
    group by student_id,subject_name
) b on a.student_id=b.student_id and a.subject_name=b.subject_name
order by a.student_id,a.subject_name

CSDN illiterate old Gu's blog , https://blog.csdn.net/superwfei

1321. Restaurant Turnover Change Growth

https://leetcode.cn/problems/restaurant-growth/

Forehead. . . . Correlating according to the date, you have to limit the date range of the output, which is not difficult, but it is cumbersome to write, which is close to the appearance of daily work.

The main thing is the usage of datediff in mysql and mssql, the difference is not small, you need to carefully check their grammar and difference calculation method, which date is in front and which date is in the back.

# mysql
select a.visited_on,sum(c.amount) amount,round(sum(c.amount) / 7,2) average_amount
from (
    select distinct visited_on 
    from customer c
    where exists(
        select 1 
        from customer
        where datediff(c.visited_on,visited_on)=6
    )
) a
inner join customer c on datediff(a.visited_on,c.visited_on)<=6 and datediff(a.visited_on,c.visited_on) >= 0
group by a.visited_on
order by a.visited_on
# mssql
select a.visited_on,sum(c.amount) amount,convert(decimal(16,2),sum(c.amount) * 1.0 / 7) average_amount
from (
    select distinct visited_on 
    from customer c
    where exists(
        select 1 
        from customer
        where datediff(d,visited_on,c.visited_on)=6
    )
) a
inner join customer c on datediff(d,c.visited_on,a.visited_on)<=6 and datediff(d,c.visited_on,a.visited_on) >= 0
group by a.visited_on
order by a.visited_on
# oracle
select to_char(a.visited_on,'YYYY-mm-DD') visited_on,sum(c.amount) amount,round(sum(c.amount) * 1.0 / 7,2) average_amount
from (
    select distinct visited_on 
    from customer c
    where exists(
        select 1 
        from customer
        where c.visited_on - visited_on = 6
    )
) a
inner join customer c on c.visited_on between a.visited_on - 6 and a.visited_on
group by a.visited_on
order by a.visited_on

1327. List all ordered products within a specified time period

https://leetcode.cn/problems/list-the-products-ordered-in-a-period/

Well, the date range can be described with between, so that one can drag three. As for the sales volume of not less than 100, just use having aggregation to filter it.

select p.product_name,sum(o.unit) unit 
from products p
inner join orders o on p.product_id=o.product_id
where o.order_date between '2020-2-1' and '2020-2-29'
group by p.product_name
having(sum(o.unit)>=100)

1341. Movie Ratings

https://leetcode.cn/problems/movie-rating/

Forehead. Completely two different query conditions, aggregation methods, and then get two result sets, put them together for output. . . The content of this test is not universal. . . . Forget it, just write whatever you want.

Well, the following content is not that a certain data can only use this method, but that different data are implemented in different ways, and friends can also use any database to achieve query results in a specific way .

# mysql
select * 
from (
    select name results
    from movierating m
    inner join users u on m.user_id=u.user_id
    group by name
    order by count(0) desc,name
    limit 0,1
) a
union all
select * 
from (
    select title results
    from movierating r
    inner join movies m on r.movie_id=m.movie_id
    where created_at between '2020-2-1' and '2020-2-29'
    group by title
    order by avg(rating) desc,title
    limit 0,1
) b
# oracle
select * 
from (
    select u.name results
    from movierating m
    inner join users u on m.user_id=u.user_id
    group by name
    order by count(0) desc,name
) a
where rownum=1
union all
select * 
from (
    select m.title results
    from movierating r
    inner join movies m on r.movie_id=m.movie_id
    where r.created_at between '2020-2-1' and '2020-2-29'
    group by title
    order by avg(r.rating) desc,title
) b
where rownum=1
# 一拖三,除了 mssql, * 1.0 都可以省略
select a.name results 
from (
    select a.*,row_number() over(partition by tp order by cnt desc,name) nid 
    from (
        select u.name,sum(1) over(partition by u.user_id order by r.created_at) cnt,'1' tp
        from users u
        inner join MovieRating r on u.user_id=r.user_id
        union all
        select m.title,avg(rating * 1.0),'2' tp 
        from Movies m
        inner join MovieRating r on m.movie_id=r.movie_id
        where created_at >= '2020-2-1' and created_at < '2020-3-1'
        group by title
    ) a
) a
where a.nid=1

1378. Replace Employee ID with Unique Identifier

https://leetcode.cn/problems/replace-employee-id-with-the-unique-identifier/

Ah, I went back to the left join test again, and I have no other ideas at all.

select u.unique_id,e.name 
from Employees e
left join EmployeeUNI u on e.id=u.id

1393. Capital gains and losses on shares

https://leetcode.cn/problems/capital-gainloss/

Um? This question is actually rated as medium difficulty? I didn't see it, isn't it still a problem with group and sum? Oh, is a case when considered a difficulty?

# 一拖三
select a.stock_name,sum(p) capital_gain_loss 
from (
    select s.*,(case when operation = 'Buy' then -price else price end) p
    from stocks s
) a
group by a.stock_name

1407. Top Travelers

https://leetcode.cn/problems/top-travellers/submissions/

Forehead. . . Or left join an aggregation result. . .

# oracle
select a.name,nvl(b.d,0) as travelled_distance 
from users a 
left join (
    select user_id,sum(distance) d
    from rides
    group by user_id
) b on a.id=b.user_id 
order by nvl(b.d,0) desc,a.name
# mssql
select name,isnull(d,0) travelled_distance
from users a
left join (
    select user_id,sum(distance) d
    from rides
    group by user_id
) b on a.id=b.user_id
order by d desc,name
# mysql
select name,ifnull(sum(distance),0) travelled_distance
from users a
left join rides r on r.user_id=a.id
group by a.id
order by travelled_distance desc,name

1484. Sell products grouped by date

https://leetcode.cn/problems/group-sold-products-by-the-date/

Oh, I finally used group_concat or for xml. Unfortunately, Lao Gu is not familiar with oracle, so I don’t know how to get this result in oracle.

# mysql
select sell_date,count(distinct product) num_sold,group_concat(distinct product order by product) products
from Activities
group by sell_date
order by sell_date
# mssql
select distinct sell_date,len(products) - len(replace(products,',','')) + 1 num_sold,products 
from Activities a
cross apply (
    select stuff((
        select distinct ',' + product
        from Activities 
        where sell_date=a.sell_date
        order by ',' + product
        for xml path('')
    ),1,1,'') products
) b
order by sell_date

1517. Find users with valid email addresses

https://leetcode.cn/problems/find-users-with-valid-e-mails/

Forehead. . . . This topic is easy with official regular support, but mssql does not have official regular support. . . You can only test strings. . . . Fortunately, tsql's like also has a similar regular usage, although it is not a complete regular.

# mysql
select * 
from Users
where mail regexp '^[a-zA-Z][a-zA-Z0-9_\.-]*@leetcode[\.]com$'
# oracle
select * 
from Users
where regexp_like(mail,'^[a-zA-Z][a-zA-Z0-9_\.-]*@leetcode[\.]com$')
# mssql
select *
from users 
where mail like '[a-zA-Z]%@leetcode.com'
and substring(mail,0,len(mail) - 12) not like '%[^a-zA-Z0-9_.-]%'

1527. Patients suffering from certain diseases

https://leetcode.cn/problems/patients-with-a-condition/

Uh-huh. For this topic, regex is still easier to use than like, especially when like needs or, the efficiency is too low.

# mssql
select * 
from patients
where ',' + replace(conditions,' ',',') like '%,diab1%'
# mysql
select * 
from Patients
where conditions regexp '(?<![a-z0-9A-Z])DIAB1'
# oracle
select * 
from Patients
where regexp_like(conditions,'(^| )DIAB1')

summary

Well, the 10 questions this time are quite comprehensive, especially the combination of grouped strings, which is a very common content, and then, regularization, which is also a very common content.

However, in the absence of regularization, we still have a way to change the content of the determined string. Well, this time there are two questions that use like to work around to get the correct result.

Therefore, we must understand clearly what functions each command has and what operations it can perform.

All gorgeous moves are composed of basic movements. Only by understanding all the basic content can you complete all requirements without any tricks.

insert image description here

Guess you like

Origin blog.csdn.net/superwfei/article/details/131353873