Update records from Linked table - sql

How to update records in a Existing table.
I have two tables studentinfo , studentrecords
Table : Student info:
HTID Class BadgeID Location Begindate
133 T1 .## NJ 2018-01-31
I updated BadgeID to .### in studentinfo table.
Student records table contain
ID Badge Location Name Date
133 02311.01 NJ Steve 2018-01-31
How can i update the Student records table.
Result should be:
ID Badge Location Name Date
133 02311.001 NJ Steve 2018-01-31

You shouldn't. You should remove badgeId from one of the tables, and use a JOIN to fetch it when you need it.
Repeating data in different tables is a really bad idea in a relational database. It just introduces opportunities for incompatibilities and confusion.

use join
update s
set s.badge=r.badge
from
Studentinfo s join StudentR r on s.HTID =r.id
but it seems you need select query from output
select s.TID,r.Badge,s.Location,r.Name,
,r.Date from Studentinfo s join StudentR r on s.HTID =r.id

Related

SQL Server : using another table as a 'lookup'

I am selecting some data from a table where one of the columns is a value that defines a person. The value is unique to that person but can appear multiple times in the table.
I have no documentation whatsoever on the db - the details of the person (name etc) are held in another table, but that has a different ID column and does not reference the ID in the first table.
There is a third table (stay with me!) that contains both the ID from the first table, and the id from the second table. So I'm trying to use this to create a 'link' between the two IDs, so I can then grab the person data I need from the second table. The third table contains many more records than the other two.
I've tried various joins but the data I get back always contains duplicates, and incorrect IDs. I'll try and give an example:
Table 1 (the table I'm querying):
AgentID
Date
Time
9000
1/1/2022
12:00:00
9000
1/2/2022
15:00:00
9001
1/1/2022
13:00:00
9001
1/2/2022
17:00:00
Table 2 (the user info):
UserID
Name
1000
Fred Bloggs
1001
John Smith
Table 3 (the 'link'):
UserID
AgentID
Other Data
1000
9000
…
1001
9001
1001
9001
1000
9000
1001
9001
1000
9000
etc
Neither UserID or AgentID are PKs or FKs in the respective tables (don't ask - we didn't design this....)
Is there a way to do what I'm trying to do? It seems there should be but I've hit a brick wall.
Example of what I've tried:
SELECT
table2.name, table1.date,table1.time
FROM
table2
LEFT JOIN
table3 ON table3.agentID = table1.agentID
LEFT JOIN
table2 ON table2.UserID = table3.UserID
I've tried inner and right joins as well, same results.
Do I need to be doing some sort of 'nested' join?
you should use Subquery, first you should join table1 with distinct value of table3(Link), second you should join table2 (UserInfo)with table link. following query
SELECT U.Name,
T.Date,
T.Time
FROM table1 t
JOIN (SELECT DISTINCT UserID,
AgentID
FROM table3) L
ON T.AgentID= L.AgentID
JOIN table2 U
ON L.UserID= U.UserID
you should change the query per the names of your tables.

Basic SQL statement , select staff name from staff table

Here is the requirement
I have two tables like below, OrderList is a data table which include 3 fields stored StaffId which is a foreign key from staff table. Noted that some records may not have a value in this table.
OrderList
OrderId Marketing_Staff_ID Finance_Staff_Id ManagerId
1 STAFF001 STAFF002 STAFF003
2 STAFF005 STAFF003
3 STAFF004 STAFF004 STAFF003
4 STAFF001 STAFF002 STAFF003
5 STAFF001 STAFF007
Staff
Staff_Id Staff_Name
STAFF001 Jack C.K.
STAFF002 William. C
STAFF005 Someone
I want to write a SQL statement can also select staff name for each record form OrderList, (For these records without staff ID, leave N/A in the name field)
OrderId Mkt StaffID Name Finance StaffId Name ManagerId, Name
1 STAFF001 Jack C.K. STAFF002 William. STAFF003 Chan.Chi
So how can I write the SQL? Left join or sth?
Thank you very much as I am really a beginner in SQL.
You need multiple LEFT JOINs:
select ol.orderid,
ol.marketing_staff_id,
coalesce(ms.staff_name, 'n/a') as marketing_name,
ol.finance_staff_id,
coalesce(fi.staff_name, 'n/a') as finance_name
from orderlist as ol
left join staff as ms on ms.staff_id = ol.marketing_staff_id
left join staff as fi on fi.staff_id = ol.finance_staff_id
I'll leave it up to you to add the join for the manager.
The above is ANSI SQL and should work in every DBMS. There is a slight possibility that your DBMS does not support the coalesce function which simply replaces a NULL value with something different. You will need to check the manual of your DBMS in that case.

SQL Server 2005 -Join based on criteria in table column

Using SQL Server 2005, what is the most efficient way to join the two tables in the following scenario ?
The number of records in each table could be fairly large about 200000 say.
The only way I can currently think of doing this is with the use of cursors and some dynamic SQL for each item which will clearly be very inefficient.
I have two tables - a PERSON table and a SEARCHITEMS table. The SEARCHITEMS table contains a column with some simple criteria which is to be used when matching records with the PERSON table. The criteria can reference any column in the PERSON table.
For example given the following tables :
PERSON table
PERSONID FIRSTNAME LASTNAME GENDER AGE ... VARIOUS OTHER COLUMNS
1 Fred Bloggs M 16
....
200000 Steve Smith M 18
SEARCHITEMS table
ITEMID DESCRIPTION SEARCHCRITERIA
1 Males GENDER = 'M'
2 Aged 16 AGE=16
3 Some Statistic {OTHERCOLUMN >= SOMEVALUE AND OTHERCOLUMN < SOMEVALUE}
....
200000 Males Aged 16 GENDER = 'M' AND AGE = 16
RESULTS table should contain something like this :
ITEMID DESCRIPTION PERSONID LASTNAME
1 Males 1 Bloggs
1 Males 200000 Smith
2 Aged 16 1 Bloggs
....
200000 Males Aged 16 1 Bloggs
It would be nice to be able to just do something like
INSERT INTO RESULTSTABLE
SELECT *
FROM PERSON P
LEFT JOIN SEARCHITEMS SI ON (APPLY SI.SEARCHCRITERIA TO P)
But I can't see a way of making this work. Any help or ideas appreciated.
Seeing that the SEARCHITEMS table is non-relational by nature, it seems that the cursor and dynamic SQL solution is the only workable one. Of course this will be quite slow and I would "pre-calculate" the results to make it somewhat bearable.
To do this create the following table:
CREATE TABLE MATCHEDITEMS(
ITEMID int NOT NULL
CONSTRAINT fkMatchedSearchItem
FOREIGN KEY
REFERENCES SEARCHITEMS(ITEMID),
PERSONID int
CONSTRAINT fkMatchedPerson
FOREIGN KEY
REFERENCES PERSON(PERSONID)
CONSTRAINT pkMatchedItems
PRIMARY KEY (ITEMID, PERSONID)
)
The table will contain a lot of data, but considering it only stores 2 int columns the footprint on disk will be small.
To update this table you create the following triggers:
a trigger on the SEARCHITEMS table which will populate the MATCHEDITEMS table whenever a rule is changed or added.
a trigger on the PERSON table which will run the rules on the updated or added PERSON records.
Results can then simply be presented by joining the 3 tables.
SELECT m.ITEMID, m.DESCRIPTION, m.PERSONID, p.LASTNAME
FROM MATCHEDITEMS m
JOIN PERSON p
ON m.PERSONID = p.PERSONID
JOIN SEARCHITEMS s
ON m.ITEMID = s.ITEMID
You could build your TSQL dynamically, and then execute it with sp_executesql.

UPDATE query that fixes orphaned records

I have an Access database that has two tables that are related by PK/FK. Unfortunately, the database tables have allowed for duplicate/redundant records and has made the database a bit screwy. I am trying to figure out a SQL statement that will fix the problem.
To better explain the problem and goal, I have created example tables to use as reference:
alt text http://img38.imageshack.us/img38/9243/514201074110am.png
You'll notice there are two tables, a Student table and a TestScore table where StudentID is the PK/FK.
The Student table contains duplicate records for students John, Sally, Tommy, and Suzy. In other words the John's with StudentID's 1 and 5 are the same person, Sally 2 and 6 are the same person, and so on.
The TestScore table relates test scores with a student.
Ignoring how/why the Student table allowed duplicates, etc - The goal I'm trying to accomplish is to update the TestScore table so that it replaces the StudentID's that have been disabled with the corresponding enabled StudentID. So, all StudentID's = 1 (John) will be updated to 5; all StudentID's = 2 (Sally) will be updated to 6, and so on. Here's the resultant TestScore table that I'm shooting for (Notice there is no longer any reference to the disabled StudentID's 1-4):
alt text http://img163.imageshack.us/img163/1954/514201091121am.png
Can you think of a query (compatible with MS Access's JET Engine) that can accomplish this goal? Or, maybe, you can offer some tips/perspectives that will point me in the right direction.
Thanks.
The only way to do this is through a series of queries and temporary tables.
First, I would create the following Make Table query that you would use to create a mapping of the bad StudentID to correct StudentID.
Select S1.StudentId As NewStudentId, S2.StudentId As OldStudentId
Into zzStudentMap
From Student As S1
Inner Join Student As S2
On S2.Name = S1.Name
Where S1.Disabled = False
And S2.StudentId <> S1.StudentId
And S2.Disabled = True
Next, you would use that temporary table to update the TestScore table with the correct StudentID.
Update TestScore
Inner Join zzStudentMap
On zzStudentMap.OldStudentId = TestScore.StudentId
Set StudentId = zzStudentMap.NewStudentId
The most common technique to identify duplicates in a table is to group by the fields that represent duplicate records:
ID FIRST_NAME LAST_NAME
1 Brian Smith
3 George Smith
25 Brian Smith
In this case we want to remove one of the Brian Smith Records, or in your case, update the ID field so they both have the value of 25 or 1 (completely arbitrary which one to use).
SELECT min(id)
FROM example
GROUP BY first_name, last_name
Using min on ID will return:
ID FIRST_NAME LAST_NAME
1 Brian Smith
3 George Smith
If you use max you would get
ID FIRST_NAME LAST_NAME
25 Brian Smith
3 George Smith
I usually use this technique to delete the duplicates, not update them:
DELETE FROM example
WHERE ID NOT IN (SELECT MAX (ID)
FROM example
GROUP BY first_name, last_name)

SQL query to return data from two separate rows in a table joined to a master table

I have a TWO tables of data with following fields
table1=(ITTAG,ITCODE,ITDESC,SUPcode)
table2=(ACCODE,ACNAME,ROUTE,SALMAN)
This is my customer master table that contains my customer data such as customer code, customer name and so on...
Every Route has a supervisor (table1=supcode) and I need to know the supervisor name in my table which both supervisor name and code exist in one table.
table1 has contain all names separated by ITTAG. For example, supervisor's name has ITTAG='K'; also salesman's name has ITTAG='S'.
ITTAG ITCODE ITDESC SUPCODE
------ ------ ------ -------
S JT JOHN TOMAS TF
K WK VIKI KOO NULL
Now this is the result which I want
ACCODE ACNAME ROUTE SALEMANNAME SUPERVISORNAME
------- ------ ------ ------------ ---------------
IMC1010 ABC HOTEL 01 JOHN TOMAS VIKI KOO
I hope this this information is sufficient to get the query..
Your data structure is either not clear or incomplete. It would help if you showed the actual example data for Table1 too, but there would be trouble.
SELECT t2.ACCODE, t2.ACNAME, t2.ROUTE, a1.ITDESC AS Salesman, a2.ITDESC AS Supervisor
FROM table1 AS t1
JOIN table2 AS a1 ON t1.SALMAN = a1.ITCODE
JOIN table2 AS a2 ON t1.?????? = a2.SUPCODE
It is not clear whether I've managed the join between Table1 and Table2 for the salesman information correctly; it is plausible, but the join for the supervisor should be similar, and yet there isn't a way to make that work. Hence the '??????' in the query.
The basic technique for joining twice to a single table is to cite it twice with different aliases, as shown. I usually use one letter or a letter and a digit for the aliases, as shown.