SQL: Table references - sql

Good day. I'm having a hard time figuring out how to do this:
SELECT P.GrossSalary, S.Contribution FROM Payroll AS P, SSSChart AS S WHERE
P.GrossSalary >= S.RangeStart AND P.GrossSalary <= S.RangeEnd;
I need the corresponding contribution amount from SSSChart table where the Gross Salary is between the Start and End range.
The problem is it will work on the first found matched record from Payroll table but the searching from the SSSChart table will not start from the top again for the next Payroll record, instead, will continue the search after the found record from the previous Payroll record. I tried several SQL commands but found no luck. All the help will be appreciated. (Doing this for my payroll system practice)

Do you want to query the entire Payroll table and find the corresponding contribution value from the SSSChart table for each result? Consider trying something along the lines of:
SELECT
P.GrossSalary, S.Contribution
FROM
Payroll as P
LEFT JOIN
SSSChart as S ON P.GrossSalary >= S.RangeStart AND P.GrossSalary <= S.RangeEnd
WHERE
1;
This is assuming each GrossSalary only belongs to exactly one SSSChart range.

Related

How do I create a new SQL table with a percentage column which is conditional on whether information shows up in two other tables?

I have 3 tables, the table called agg((date,sname,open,high,low,close,volume)) contains daily information for every stock for x number of past years. Another table, split(date,sname,post,pre), has info for every time any stock split. Another table, div(date,sname,dividend), has info for every time a stock had a dividend. I want to create a new table, with a column that gives the percent change from closing of the previous day, to the day after, for every stock and every day listed in agg.
Here is the line I have for just the daily change, not including div and split:
create table daily
as
with prevclose as (
select date,sname,close,
lag(close) over (partition by symbol order by date) pclose
from agg
)
select a.*,
100.0*(close - pclose)/(case when pclose=0 then null else pclose end) as prcnt
from prevclose a
where pclose != 0;
I want to change this code to incorporate the change in split and dividends which is not incorporated in the agg table. I don't even need the full calculation for this, but I need help figuring out how to incorporate the condition into the new table. I only need to add in split and div info if there is split and div info for that particular date and time. I think if I could just see the query for a similar problem it would help.

Records between 2 dates Oracle SQL

I am looking to filter out records between 2 dates. Here is a list of start and end dates. I need identify records that fall under the respective periods.
I am able to identify the records that fall in the first and last period i.e. first (9/07/2020 - 22/07/2020) and last (10/11/2020 - 23/12/2020) by using MIN and MAX. I am not able to find records that fall in between i.e. 2-11?
I have another table that shows a date when the records were updated. For instance,
I need to identify the records that falls under what periods. For instance,
Any kind of help would be appreciated!
Thanks
You need to do a join on your two tables. You don't give your table names, so this is a bit of guesswork, but try something like this:
select *
from period_table p
inner join record_table r on r.changed_date between p.startdate and p.enddate

SQL query for percentage change compared to previous date

I have a table within access containing the performance of departments on different reference dates. All data is within one table "tblmain". The table contains the following fields:
reference date (called "ref_date", formatted dd.mm.yyyy)
department identifier (called "dep_id")
performance value (called "val")
Every reference date consists of round about 100 departments and every week I import a new reference date.
My goal now is to build a query which calculates the percentage change from on reference date compared to the previous reference date. Furthermore, it should only show the departments with a change bigger than 5%.
I am currently stuck. I have created a query that gives me the val from the previous reference date but only for one specific department. And I do not know how to continue. This query looks as follows:
SELECT TOP 1 tblmain.val
FROM (SELECT TOP 2 tblmain.val, tblmain.ref_date FROM tblmain WHERE dep_id=1 ORDER BY tblmain.ref_date DESC)
ORDER BY tblmain.ref_date;
I would appreciate any feedback. After finishing this query, I plan to use this query in a form where I can choose an reference date and threshold.
Many thanks in advance!
Query to pull prior val for each record:
SELECT tblMain.ID, tblMain.ref_date, tblMain.dep_id, tblMain.val,
(SELECT TOP 1 val FROM tblMain AS Dupe
WHERE Dupe.dep_id=tblMain.dep_id AND Dupe.ref_Date < tblMain.ref_date
ORDER BY dupe.ref_date) AS PriorVal
FROM tblMain;
Now use that query to calculate percentage:
SELECT Query1.*, Abs(([PriorVal]-[val])/[PriorVal]*100) AS P
FROM Query1
WHERE (((Abs(([PriorVal]-[val])/[PriorVal]*100))>5));

SQL: Find nth order for nth customer

I am quite new to SQL, have been learning for ~3 weeks, and have taken a liking to it. Hoping to polish up my skills before beginning to apply to Data Analyst roles.
I've been working with a dummy dvd-rental database and have found myself unable to solve a challenge given to me by a peer. The question was: "what is the most expensive rental for the 4th customer?"
We can see in picture, that based on the nth_customer column, Terrance Roush is the 4th ever customer (he's the 4th ever person to pay). But the issue is that the nth_customer column is actually reporting back the nth order and continues counting to infinity. So the next time Terrance shows up, the nth_customer column will not show '4' (which is what I was hoping to achieve).
Would appreciate any feedback on how to solve this. Thank you in advance.
If "the fourth customer" means the customer who did the fourth rental, you can break the problem down into two - finding that fourth customer, and finding their most expensive rental. Something like this:
SELECT *
FROM payment
WHERE customer_id = (
SELECT customer_id
FROM payment
ORDER BY payment_date
LIMIT 1 OFFSET 3
)
ORDER BY amount DESC
LIMIT 1;
Here I'm finding the ID of the fourth customer in the subquery, using a LIMIT & OFFSET to get just the one record I want. Then in the outer query I'm simply ordering all of that customer's records and taking the one with the biggest amount.

How to count employees that have been promoted?

I'm trying to figure out how to come up with a calculation or query to count the number of employees by grade promoted on each pay period.
*count the number of records who's value in grade have increased by pay period.
Sample solution:
Soln:
Year Payroll Period Count
2018 16 2
2019 6 1
2019 10 1
I've tried pivot and queries in access but I think this needs to have an inner join to identify specific employees who got promoted. thanks for the assistance.
code in excel that seems to work but needs to be transferred in access due to the number of records. I think inner join would make this work. =AND(B2<>B3,C2=C3,D3>D2)
Based on EXCEL, you can derive your solution, assuming that your records are in sequence for columns Year, Payroll, Employee & Grade.
Add another column to determine if there is a grade increase for that particular Payroll Period.
For excel cell reference sake, "Year" is in cell A1
Set formula of 1st cell of this column to false
For the next cell in this new column, set it as such:
The above checks if there is a grade increase for that particular Payroll Period.
The explanation of the formula in sequence is as such, 1. Check if year same (A3=A2), 2. Check if Payroll Period is different(B3<>B2), 3. Check if Employee is the same (C3=C2) and finally 4. Check if there is a change in grade (D3=D2).
Copy this formula down to the rest of your range.
Next, you can start to pivot.
Add your pivot table from your table/range with the following
Filter Grade Increase to true and also change the values aggregation of Employee from Sum to Count.
You will get the following:
I would rename Count of Employees to make it more meaningful.
One caveat for the above approach is that if the grade was increased at the beginning of the 1st Payroll Period of the year, the increase won't be captured. For such, you can remove the year check from the formula A3=A2.
Edit:
Doing a bit of research, perhaps you can do
select t1.*, (t1.Grade > t2.Grade) as Grade_Increase
from YourTableName t1 left join YourTableName t2 on
t1.Employee = t2.Employee and
(((t1.Year - 2018)*26) + t1.Payroll_Period) =
(((t2.Year - 2018)*26) + t2.Payroll_Period - 1) -- -1 to get the prior record to compare grades
What the above does is essentially joining the table to itself.
Records that are 'next in sequence' are combined into the same row. And a comparison is done.
This was not verified in Access.
Substitute 2018 with whatever your base year is. I'm using 2018 to calculate the sequence number of the records. Initially I thought of using common table expressions, rank and row_number. But access doesn't seem to support these functions.