to create a table from multiple tables without affecting datawarehouse - qlikview

I want to create a table in qlikview from multiple tables without affecting the datawarhouse. Also synthetic keys are found and how to remove them.
empLeave:
LOAD SickLeaveHours ,
VacationHours ;
SQL SELECT SickLeaveHours,
VacationHours
FROM databaseConnection;
empDetails:
LOAD BirthDate,
EmployeeID ,
Gender,
Title;
SQL SELECT BirthDate,
EmployeeID,
Gender,
Title
FROM databaseConnection;
empAddress:
LOAD AddressID,
ModifiedDate;
SQL SELECT AddressID,
ModifiedDate
FROM databaseConnection;
empDepartment:
LOAD DepartmentID,
GroupName,
Name;
SQL SELECT DepartmentID,
GroupName,
Name
FROMdatabaseConnection;
empRate:
LOAD PayFrequency,
Rate;
SQL SELECT PayFrequency,
Rate
FROM databaseConnection;
empshift:
LOAD EndTime,
Name as name,
ShiftID,
StartTime;
SQL SELECT EndTime,
Name,
ShiftID,
StartTime
FROM databaseConnection;
//need to make newtable with EmployeeiD,ShiftID,Vaccationhours, SickleaveHours,departmentID
Required to make table named as newtable with measures of
EmployeeID
ShiftID
Rate
SickLeaveHours
VacationHours
DepartmentID

Related

How to transform Access data similar to crosstab

I have data that I want to display similar to a cross-tab query but not quite. The data I have looks like this with each segment of data on a different row:
I want the data to be consolidated to be all on one row for each client, like this:
I've attempted this with a cross-tab query but I'm not wanting to total any of the fields and there are several data point for each product (Type, Name, PurchaseDate, etc).
Any help is greatly appreciated!
Not a very practical presentation of data but it is possible. Need a unique identifier field - autonumber should serve - I called it RID. Consider:
Query 1:
SELECT RID, ID, FirstName, LastName, Dept, ProductType AS Data, "PT" AS Cat FROM Table1
UNION SELECT RID, ID, FirstName, LastName, Dept, ProductName, "PN" FROM Table1
UNION SELECT RID, ID, FirstName, LastName, Dept, PurchaseDate, "PD" FROM Table1
UNION SELECT RID, ID, FirstName, LastName, Dept, PurchaseCost, "PC" FROM Table1
UNION SELECT RID, ID, FirstName, LastName, Dept, DeliveryDate, "DD" FROM Table1;
Query 2:
TRANSFORM First(Query1.Data) AS FirstOfData
SELECT Query1.ID, Query1.FirstName, Query1.LastName, Query1.Dept
FROM Query1
GROUP BY Query1.ID, Query1.FirstName, Query1.LastName, Query1.Dept
PIVOT DCount("*","Query1","ID=" & [ID] & " AND Cat='" & [Cat] & "' AND RID<" & [RID])+1 & [Cat];
However, there is a limit of 255 fields so there may be more data than can be handled.

after doing left join i am getting duplicate entries. Need to know how to remove duplicate entries

LOAD EmployeeID,
SickLeaveHours,
(8760-SickLeaveHours-VacationHours)as QualityTimeHours,
(8760-SickLeaveHours-VacationHours)/24 as QualityDays,
((8760-SickLeaveHours-VacationHours)/24)/30 as QualityMonths,
VacationHours;
SQL SELECT EmployeeID,
SickLeaveHours,
VacationHours
FROM Database;
Join
LOAD * INLINE [
F1, F2
ShiftID, Shift
1, DAY
2, EVENING
3, NIGHT
];
left join(fact)
b:
LOAD
AddressID,
EmployeeID;
SQL SELECT
AddressID,
EmployeeID
FROM Database;
left join(fact)
c:
LOAD
DepartmentID,
EmployeeID;
SQL SELECT
DepartmentID,
EmployeeID
FROM Database;
left join(fact)
LOAD ShiftID;
SQL SELECT ShiftID
FROM Database;
left Join (fact)
d:
LOAD EmployeeID,
Rate;
SQL SELECT
EmployeeID,
Rate
FROM Database ;
empDetails:
LOAD BirthDate,
EmployeeID,
Gender,
Title;
SQL SELECT BirthDate,
EmployeeID,
Gender,
Title
FROM Database ;
Department:
LOAD DepartmentID,
GroupName,
Name;
SQL SELECT
DepartmentID,
GroupName,
Name
FROM Database;
Address:
LOAD AddressID,
ModifiedDate,
rowguid;
SQL SELECT
AddressID,
ModifiedDate,
rowguid
FROM Database;
shift:
LOAD EndTime,
Name as name,
ShiftID,
StartTime;
SQL SELECT
EndTime,
Name,
ShiftID,
StartTime
FROM Database;
Expected table with no duplicate entries
You are getting duplicates because almost all tables are joined to the fact table and some of these tables dont have common keys which leads to cross join. For example:
left join(fact)
LOAD ShiftID;
SQL SELECT ShiftID
FROM Database;
The script above loads only one field ShiftID which do not exists in the fact table and the join will basically perform cross join (all-to-all)
Qlik joins tables on common field names. If you need to join two tables then these tables should have at least one common field. In your example: fact and EmpAddress tables will be joined/linked on EmployeeID field.
Another point: dont try and always join tables into one. Sometimes is better to just link them. Otherwise you can get wrong/duplicated answers.
For example: fact table can have multiple rows per EmployeeID and if you join (not link) EmpDetails table to fact and then count the Gender field you will get wrong/duplicated answer. In one to many case just link the tables (both tables should have common field(s) but they are not joined. Qlik will automatically link them)
The script below is a version of yours without the "hard" joins to fact (dont think you need these joins)
And also - the shifts data is not going to be linked to anything since it doesent have any common field with the employee tables
fact:
LOAD
EmployeeID,
SickLeaveHours,
(8760-SickLeaveHours-VacationHours)as QualityTimeHours,
(8760-SickLeaveHours-VacationHours)/24 as QualityDays,
((8760-SickLeaveHours-VacationHours)/24)/30 as QualityMonths,
VacationHours;
SQL SELECT EmployeeID,
SickLeaveHours,
VacationHours
FROM Database;
EmpAddress:
LOAD
EmployeeID,
AddressID;
SQL SELECT
AddressID,
EmployeeID
FROM Database;
EmpDepartment:
LOAD
EmployeeID,
DepartmentID;
SQL SELECT
DepartmentID,
EmployeeID
FROM Database;
EmpRate:
LOAD EmployeeID,
Rate;
SQL SELECT
EmployeeID,
Rate
FROM Database;
EmpDetails:
LOAD
EmployeeID,
BirthDate,
Gender,
Title;
SQL SELECT BirthDate,
EmployeeID,
Gender,
Title
FROM Database ;
Department:
LOAD
DepartmentID,
GroupName,
Name as DeprtmentName;
SQL SELECT
DepartmentID,
GroupName,
Name
FROM Database;
Address:
LOAD AddressID,
ModifiedDate as Address_ModifiedDate,
rowguid;
SQL SELECT
AddressID,
ModifiedDate,
rowguid
FROM Database;
// This part of the script will be isolated from the rest
// because there is no key to join on
shift:
LOAD
Name as ShiftName,
ShiftID,
EndTime,
StartTime;
SQL SELECT
EndTime,
Name,
ShiftID,
StartTime
FROM Database;
Join
LOAD * INLINE [
ShiftID, Shift
1, DAY
2, EVENING
3, NIGHT
];
// Is this table needed at all?
LOAD ShiftID;
SQL SELECT ShiftID
FROM Database;

Deleting duplicates in a table based on a criteria only in SQL

Let's say I have a table with columns:
CustomerNumber
Lastname
Firstname
PurchaseDate
...and other columns that do not change anything in the question if they're not shown here.
In this table I could have many rows for the same customer with different purchase dates (I know, poorly designed... I'm only trying to fix an issue for reporting, not really trying to fix the root of the problem).
How, in SQL, can I keep one record per customer with the latest date, and delete the rest? A group by doesn't seem to be working for my case
;with a as
(
select row_number() over (partition by CustomerNumber, Lastname, Firstname order by PurchaseDate desc) rn
from <table>
)
delete from a where rn > 1
This worked for me (on DB2):
DELETE FROM my_table
WHERE (CustomerNumber, Lastname, Firstname, PurchaseDate)
NOT IN (
SELECT CustomerNumber, Lastname, Firstname, MAX(PurchaseDate)
FROM my_table
GROUP BY CustomerNumber, Lastname, FirstName
)
SELECT CustomerNumber, Lastname, Firstname, MAX(PurchaseDate) LatestPurchaseDate
FROM Table
GROUP BY CustomerNumber, Lastname, Firstname
The MAX will select the highest (latest) date and show that date for each unique combination of the GROUP BY columns.
EDIT: I misunderstood that you wanted to delete records for all but the latest purchase date.
WITH Keep AS
(
SELECT CustomerNumber, Lastname, Firstname, MAX(PurchaseDate) LatestPurchaseDate
FROM Table
GROUP BY CustomerNumber, Lastname, Firstname
)
DELETE FROM Table
WHERE NOT EXISTS
(
SELECT *
FROM Keep
WHERE Table.CustomerNumber = Keep.CustomerNumber
AND Table.Lastname = Keep.Lastname
AND Table.Firstname = Keep.Firstname
AND Table.PurchaseDate = Keep.LastPurchaseDate
)

SQl server query multiple aggregate columns

I need to write a query in sql server to data get like this.
Essentially it is group by dept, race, gender and then
SUM(employees_of_race_by_gender),Sum(employees_Of_Dept).
I could get data of first four columns, getting sum of employees in that dept is becoming difficult.
Could you pls help me in writing the query?
All these details in same table Emp. Columns of Emp are Emp_Number, Race_Name,Gender,Dept
Your "num_of_emp_in_race" is actually by Gender too
SELECT DISTINCT
Dept,
Race_name,
Gender,
COUNT(*) OVER (PARTITION BY Dept, Race_name, Gender) AS num_of_emp_in_race,
COUNT(*) OVER (PARTITION BY Dept) AS num_of_emp_dept
FROM
MyTable
You should probably have this
COUNT(*) OVER (PARTITION BY Dept, Gender) AS PerDeptRace
COUNT(*) OVER (PARTITION BY Dept, Race_name) AS PerDeptGender,
COUNT(*) OVER (PARTITION BY Dept, Race_name, Gender) AS PerDeptRaceGender,
COUNT(*) OVER (PARTITION BY Dept) AS PerDept
Edit: the DISTINCT appears to be applied before the COUNT (which would odd based on this) so try this instead
SELECT DISTINCT
*
FROM
(
SELECT
Dept,
Race_name,
Gender,
COUNT(*) OVER (PARTITION BY Dept, Race_name, Gender) AS num_of_emp_in_race,
COUNT(*) OVER (PARTITION BY Dept) AS num_of_emp_dept
FROM
MyTable
) foo
Since the two sums you're looking for are based on a different aggregation, you need to calculate them separately and join the result. In such cases I first build the selects to show me the different results, making it easy to catch errors early:
SELECT Dept, Gender, race_name, COUNT(*) as num_of_emp_in_race
FROM Emp
GROUP BY 1, 2, 3
SELECT Dept, COUNT(*) as num_of_emp_in_dept
FROM Emp
GROUP BY 1
Afterwards, joining those two is pretty straight forward:
SELECT *
FROM ( first statement here ) as by_race
JOIN ( second statement here ) as by_dept ON (by_race.Dept = by_dept.Dept)

How we can use CTE in subquery in sql server?

How we can use a CTE in a subquery in SQL Server?
like:
SELECT id (I want to use CTE here), name FROM table_name
Just define your CTE on top and access it in the subquery?
WITH YourCTE(blubb) AS
(
SELECT 'Blubb'
)
SELECT id,
(SELECT blubb FROM YourCTE),
name
FROM table_name
It doesn't work:
select id (I want to use CTE here), name from table_name
It's not possible to use CTE in sub queries.
You can realize it as a work around:
CREATE VIEW MyCTEView AS ..here comes your CTE-Statement.
Then you are able to do this:
select id (select id from MyCTEView), name from table_name
Create a view with CTE/ Multiple CTEs with UNION sets of all CTEs
CREATE VIEW [dbo].[_vEmployees]
AS
WITH
TEST_CTE(EmployeeID, FirstName, LastName, City, Country)
AS (
SELECT EmployeeID, FirstName, LastName, City, Country FROM Employees WHERE EmployeeID = 4
),
TEST_CTE2
AS (
SELECT EmployeeID, FirstName, LastName, City, Country FROM Employees WHERE EmployeeID = 7
)
SELECT EmployeeID, FirstName, LastName, City, Country FROM TEST_CTE UNION SELECT * FROM TEST_CTE2
GO
Now, use it into sub query
SELECT * FROM Employees WHERE EmployeeID IN (SELECT EmployeeID FROM _vEmployees)