SQL Server 2008 Array Query - sql

I have a table structure
ID [integer]
Name
RecoveryID [integer]
date
I want to search on the RecoveryID with an array and reveal all those in the array without a corresponding record.
so, if my table contains
1,'John',1,20-10-2013
2,'John',4,20-10-2013
3,'John',5,20-10-2013
And I search on the RecoveryID with the array [1,2,3,4,5,6] I would want the result [2,3,6]
I have tried using various IN, NOT IN statements, but I always get what I have, not what I don't have.
To try and explain further, I am trying to Outer Join without a second table. I have a list of users, a list of things that CAN be done (1,2,3,4,5,6,7) and a list of things that NEED to be done by a specific user. {[John],(1,2,7)} For example.
If John completes action 1, my work table now contains ('John',1,20-10-2013) actions 2 & 7 are remaining. I have the list (1,2,7) how can I query the work table so that it returns (2,7) ?

You can use Except set operation as :
SELECT n
FROM (VALUES(1),(2),(3),(4),(5),(6)) AS Nums(n)
EXCEPT
SELECT RecoveryID from table1

Related

BigQuery Create Table Query from Google Sheet with Variable item string field into Repeated Field

I hope I explain this adequately.
I have a series of Google Sheets with data from an Airtable database. Several of the fields are stringified arrays with recordIds to another table.
These fields can have between 0 and n - comma separated values.
I run a create/overwrite table SELECT statement to create native BigQuery tables for reporting. This works great.
Now I need to add the recordIds to a Repeated field.
I've manually written to a repeated field using:
INSERT INTO `robotic-vista-339622.Insurly_dataset.zzPOLICYTEST` (policyID, locations, carrier)
VALUES ('12334556',[STRUCT('recordId1'),STRUCT('recordId2')], 'name of policy');
However, I need to know how I to do this using SELECT statement rather than INSERT. I also need to know how to do this if you do not know the number of recordIds that have been retrieved from Airtable. One record could have none and another record could have 10 or more.
Any given sheet will look like the following, where "locations" contains the recordIds I want to add to a repeated field.
SHEETNAME: POLICIES
|policyId |carrier | locations |
|-----------|-----------|---------------------------------|
|recrTkk |Workman's | |
|rec45Yui |Workman's |recL45x32,recQz70,recPrjE3x |
|recQb17y |ABC Co. |rec5yUlt,recIrW34 |
In the above, the first row/record has no location Id's. And then three and two on the subsequent rows/records.
Any help is appreciated.
Thanks.
I'm unsure if answering my own question is the correct way to show that it was solved... but here is what it took.
I create a Native table in BigQuery. the field for locations is a string, mode repeated.
Then I just run an overwrite table SELECT statement.
SELECT recordId,Name, Amount, SPLIT(locations) as locations FROM `projectid.datasetid.googlesheetsdatatable`;
Tested and I run linked queries on the locations with unnest.

MS Access - Counting Occurrences of a word in multiple columns

I have a database with a couple tables that tracks personnel errors that require rework by another person. Basically, a person on the job could rework up to 10 different work packages by other people throughout their shift. To make it easy, I just have columns in the table for rework_1/original_worker_1/rework_comment_1 (repeated up to 10) and the person who had to rework it. All of my worker's names are in a separate table so I can add people and my forms update dynamically with their names. What I want to do is this:
Pull a person from my worker's name table.
Search for all occurrences of their name in another table in in column original_worker_X (where X is 1 - 10).
Output the values: Workers Name / How Many Times I found it in the original_worker_X columns.
From here I would need to make a bar graph so that each person's name had a bar with how many times someone had to rework something they did originally.
If I could do this with PHP and MySQL I would be in the money because I could brute force something with some PHP variables, queries, and loops but I am an access novice at best! I appreciate any help you wizards can provide.
Table 1:
Table 2:
Expected Output Numbers:
so i will suggest you do the following
Create a new table,lets say table 3 with three fields
A. ID, pkey, auto number
B. original_worker, text field
C. Person_doing_rework, text field
You will need ten insert statements that will insert each of the original worker 1-10, as well as person doing re-work , this is to a normalise table
Currently, the design of your table is a bit crude, and having a select statement with group by columns numbering 10 is not achievable
Below are samples of the insert statements
INSERT INTO Table3 (original_worker,Person_doing_rework)
SELECT original_worker1,Person_doing_rework
FROM table2 where isnotNull(original_worker1)
INSERT INTO Table3 (original_worker,Person_doing_rework)
SELECT original_worker2,Person_doing_rework
FROM table2 where isnotNull(original_worker2)
replicate this for original_worker3 to original_worker10
Third step
You need a delete statement that will delete all from table 3, this is to ensure that the records from table 3 is not duplicated, since we don't have a pkey/fkey relationship between table 2 and 3
Fourth step
Place all the queries into a macro in the following order
A. Delete query to run first
B. Insert queries to run next
Fifth step
Add a msgbox in the macro, that will run last, this is to inform you that all the other macro steps, i.e A and B above has successfully run.
Sixth step
You can now have a select statement from table 3 that can count the number of times an original workers' work is re worked upon, because you now have two main fields in table 3, one for original_work, and two for Person_reworked.
So any time you want to find out how many times some ones work has been re worked upon, you have to just click the macro button, this will run all the queries and put values you need in the table 3, after which you can view the details via the query in step 6.
SELECT original_worker, Count(Person_doing_rework), FROM table3 GROUP BY original_worker;

SQL or statement vs multiple select queries

I'm having a table with an id and a name.
I'm getting a list of id's and i need their names.
In my knowledge i have two options.
Create a forloop in my code which executes:
SELECT name from table where id=x
where x is always a number.
or I'm write a single query like this:
SELECT name from table where id=1 OR id=2 OR id=3
The list of id's and names is enormous so i think you wouldn't want that.
The problem of id's is the id is not always a number but a random generated id containting numbers and characters. So talking about ranges is not a solution.
I'm asking this in a performance point of view.
What's a nice solution for this problem?
SQLite has limits on the size of a query, so if there is no known upper limit on the number of IDs, you cannot use a single query.
When you are reading multiple rows (note: IN (1, 2, 3) is easier than many ORs), you don't know to which ID a name belongs unless you also SELECT that, or sort the results by the ID.
There should be no noticeable difference in performance; SQLite is an embedded database without client/server communication overhead, and the query does not need to be parsed again if you use a prepared statement.
A "nice" solution is using the INoperator:
SELECT name from table where id in (1,2,3)
Also, the IN operator is syntactic sugar built for exactly this purpose..
SELECT name from table where id IN (1,2,3,4,5,6.....)
Hoping that you are getting the list of ID's on which you have to perform a query for names as input temp table #InputIDTable,
SELECT name from table WHERE ID IN (SELECT id from #InputIDTable)

Best approach to embed subquery results

Currently I have a web application (JSF 2.0 and SQL Server) where values for tDataTable are retrieved using a Query A and then based on retrieved result we run another query to retrieve associated details.
for example :
Query A: returns all Restaurants in User selected Area (let's imagine there are 1000s)
Query B: Based on Returned Result (Above) , Query B retries reviews for each restaurant using the RestaurantPK value.
So the way it's done now, if there are 200 rows once Query A has executed, We call Query B 200 Times to retrieve review information for each restaurant.
So my question is how can i make more efficient? What is the standard practice in these cases? I chose the title as "Best approach to embed Sub-query result" as i suspect a sub-query will need to be used in Query A , but cannot figure out how it would work, given for each restaurant(Row) there could be 10-15 reviews).
UPDATE:
I had tried JOIN before posting my question here but problem was i was only getting one review for each restaurant instead of all available reviews for each restaurant. I'm starting to think the only way to do this would be to Write a storedProcedure where once A is executed I'll store the result in a #temp table, loop through the result and retrieve all the reviews for each restaurant and insert them back into the #temp table where if one resturant has 10 reviews, they will be separated by ; and back in java I'll split them back into a meaningful format. that way i am still returning just one row for each restaurant but with embedded reviews as one of columns.
so i would have:
Resturnat, Location, Phone......Reviews
X,Sydney,1234,.....,AAAAAAA;BBBBBBBB;CCCCCCCCC;
Comments?
Use joins in SQL, so you can get all data in 1 query.:
Select rest.id, reviews.text
from restaurants rest
inner join reviews on reviews.rest_id = rest.id
where some conditions for restaurants
You haven't said how you are 'displaying' this data so can't recommend an absolute best approach. I would say your 2 options are
A join that returns all reviews - the restaurant information will be duplicated for each row so when displaying you should loop through and check if the current row's RestaurantPK is different to the previous and only display the info then.
Return 2 tables form the SQL server. Load the results of Query A into a #temp or #temp table and then do something like
SELECT * from #temp
SELECT * FROM reviews WHERE RestaurantPK IN (SELECT RestaurantPK from #temp)
although obviously selecting your columns by name rather than *

Search across Columns and replace text

I have an Access database of information where I need to replace text that may reside in 1 of 10 columns. I have a number of different requests for find and replace that need to be done. I need to do this twice a day.
These are the details. We receive a download of data twice a day that has course information in it. A record can have 10 courses in it. Some of the courses need to be combined. For instance
Course 1 is 12345, there are 2 other courses that are the same and therefore course 2(01234), Course 3(34566) all need to be changed to 12345. I also need to combine other course in a similar fashion, since I need to do this twice a day, ideally I would like to have a table with just columns of find and replace and use it to pick up the changes and reference it in my sql code.
An easy way to do this is the key!
Have you considered a cross reference table of something like
Table1
MCourse Subcourse
12345 2(01234)
12345 3(34566)
Then you can do updates like
Set mainTable.Desiredfield = Table1.Mcourse
where desiredfield = subcourse
Or you can create a query that uses the cross reference table to select the desired value and make a new table from that.