Select all names where none of that names entries are approved - database

I have a table that contains an name field and an approved field. However multiple entries can have the same name. I have been trying to write a query that finds all unique names and decides if it has no approved entries
I feel like I need to use a join but I can only really join it with itself. Is there a function that does this that I'm just not finding? Or do i need to use some weird kind of join to make this work.

define variable isApproved as logical no-undo.
for each customer no-lock break by name:
if first-of( name ) then isApproved = no.
if approved then isApproved = yes.
if last-of( name ) and isApproved = no then display name.
end.

I had a problem exactly like yours about 6 months ago. I've used a solution like this. Hope it helps.
DEF TEMP-TABLE tt-name NO-UNDO
FIELD name AS CHAR
FIELD approved AS LOG
INDEX ch-unique IS PRIMARY UNIQUE
name.
/* Create a list of unique customers */
FOR EACH customer FIELDS(name) NO-LOCK:
IF NOT CAN-FIND(FIRST tt-name
WHERE tt-name.name = customer.name) THEN DO:
CREATE tt-name.
ASSIGN tt-name.name = customer.name.
END.
END.
/* Look for at least one customer who matches name and not approved */
FOR EACH tt-name:
IF CAN-FIND(FIRST customer NO-LOCK
WHERE customer.name = tt-name.name
AND NOT customer.approved) THEN
ASSIGN tt-name.approved = NO.
ELSE
ASSIGN tt-name.approved = YES.
END.
/* Display the results */
FOR EACH tt-name
WHERE NOT tt-name.approved:
DISP tt-name WITH WIDTH 333 NO-ERROR.
END.

Related

Apex Get Account Record Ids where Contact First Name is in LIST ( using AND Condition )

In Salesforce I would like to retrieve AccountIds where its related Contact FirstName must have values in list of String. List of string is {'Test','User'}. I would need to find all Accounts where Contact first Name has both Test and User as related Contacts,
I am trying as below but the below query will show accounts where even 1 value matches as Contact First Name.
List<String> names = new List<String>{'Test','User'}; List<Account> accountList =         [ Select Id from Account Where Id IN         (Select AccountId FROM Contacts where FirstName LIKE :names)];
Please help
SELECT Id, Name
FROM Account
WHERE Id IN (SELECT AccountId FROM Contact WHERE LastName = 'Test')
AND Id IN (SELECT AccountId FROM Contact WHERE LastName = 'User')
But it'll work only 2 times, you can't write 3rd "IN" like that (see here).
If you need a more generic solution that can take lists of any size you'd have to run "my" queries in loop, 2 names at a time, save results to some Set<Id> or Map, play with functions like myset.retainAll(idsFromCurrentLoopQuery)... Of course query in a loop is bit evil too.

Search for a value in two columns in two different tables with SQL?

I want a code to search for a value in two columns in two different SQL tables ,
a = raw_input('Enter name here')
cur.execute('SELECT phone FROM participants')
b = cur.fetchall()
if a in b:
print "The name is already exist"
Here I searched in on table (participants). What should I do to search in two tables?
Assuming you are asking for SQL statement, you need to just use select from two tables instead of one. To keep everything in single statement, you can use UNION as described eg. here: https://www.w3schools.com/sql/sql_union.asp
Let's assume you have second table, named friends with phone field also there.
Then, your SQL will be like this:
SELECT phone FROM participants where name = <input name here>
UNION
SELECT phone FROM friends where name = <input name here>
You can add sort at the end, if this is relevant for your case.
This you can also search more than one column in each table, by adding "or" clause, like this:
SELECT phone FROM participants where name = <your input here> or lastname = <your input here>
UNION
SELECT phone FROM friends where name = <your input here> or lastname = <your input here>
Of course, you have to replace with proper search string.
BTW, the code you provided is not searching anything - it is just dumping all phones from the table into "b" variable, which may be very inefficient especially when the table grows large. I strongly suggest to search via SQL and then present your output from script.

Checking existance of dynamic value before update/insert

I am trying to mass update a table column with values but I need to get the query to check whether this value already exists. If it does then to make the relevant changes before checking again and updating the table.
The database primarily holds staff information and I need to create a unique username, the script to create the username is :
select upper(LEFT(first_name,1))+LEFT(surname,3)+'1'
from staff_test
If this was used for an example user it would generate a username of ABit1 for user Andrew Bithell. What I need it to do is check to see if there already is a ABit1 username in the STAFF_TEST table and if so change Andrews username to ABit2 as the usernames have to be unique before it moves onto the next user.
I have created another table which lists all the current usernames splitting the existing usernames into 2 columns, so they display in this table as
column1 | column2
------------------
ABit |1
I have experimented with a function and I am now thinking a Merge statement might be the way to go.
Any suggestions are welcomed.
Use row_number can generate all the unique names at once:
select
upper(LEFT(first_name,1))+LEFT(surname,3)+
rtrim(row_number() over (partition by upper(LEFT(first_name,1))+LEFT(surname,3) ))
,first_name
,surname
from staff_test
Perform an up front check to see if there are any clashes:
SELECT UPPER(LEFT(first_name, 1)) + LEFT(surname, 3) + '1' AS username ,
COUNT(1) counter
FROM staff_test
GROUP BY UPPER(LEFT(first_name, 1)) + LEFT(surname, 3) + '1'
HAVING COUNT(1) > 1
ORDER BY COUNT(1) DESC
This will return each username on your staff table, grouped by the username, along with a count of how many occurrences there are of each.
You can either sanitize the data if that's what you're looking to do, otherwise I would suggest, appending an Id column value or some other unique value per record instead of 1 on the end.

Using INDEX in SQL Server

I need to create am index in SQL however it needs to display the records by entering only a part of the name. The index should be created to retrieve the student information using part of the student name (i.e. if the name if Johnanesburg; the user can input John)
I used the syntax below but it wont work
create index Student ON Student(SName)
SELECT * FROM Student WHERE StRegNo LIKE A%
go
I think your problem is here: A%
Try wrapping it in apostrophes.
SELECT *
FROM Student
WHERE StRegNo LIKE 'A%'
Also, you may want a GO statement after you create your index.
The index you are creating over SName will not provide as much benefit for the select statement you are running as one created over StRegNo. Assuming that StRegNo is the primary key on the Student table you could try:
CREATE CLUSTERED INDEX IX_Student on Student(StRegNo)
SELECT *
FROM Student
WHERE StRegNo LIKE 'A%'
However it appears that the SQL you have provided is at odds with your question. If you want to search based on student name then you might want the following instead.
CREATE NONCLUSTERED INDEX IX_Student on Student(SName)
SELECT *
FROM Student
WHERE SName LIKE 'A%'
Ardman got it right regarding your query %A => '%A'. Now as for the index, that's another story that no index can help you with at the time, neither can full text search. If you want to look for names starting with #A (i.e. John%), an ordered index could help but otherwise (i.e. %bur%), you will go for a full table scan !

SQL Database design help needed

I am trying to limit the about of tables in my database because I hear that's good (I am a novice web developer). I want to have the user input a list into the database. So they input a title, overall comment, and then start making the list. I can't figure out how to do this without making a new table for each list. Because, say one user wants a list with 44 values and another user wants a list of 10 values. I can't think of how to do this without making a new table for each list. I would really appreciate any help/insight you can give to me.
Basically, you want to make a table for the user lists, where each row in the table refers to one user's lists, and another table for the user list values, where each row in the table has a column for a reference to the list it belongs to, and a column for the value the user input.
Your Table Could Be:
UserID, int
ListID, int (Primary Key-Unique Identifier)
Title, VarChar(250)
Comment, VarChar(MAX)
Example Content:
1 | 1 | The Title | My Comment
1 | 2 | The Other Title | My other comment
2 | 3 | First Comment | Second Person, first comment
Eacher User just gets their list from a query:
Select ListID, Titel, Comment FROM the_Table
where UserID = #UserID
You can get away with a single table of lines for all the lists, say for example simply
CREATE TABLE ListLines (
listID INTEGER,
lineNo INTEGER,
line TEXT,
PRIMARY KEY (listID, lineNo),
FOREIGN KEY (listID) REFERENCES Lists
);
with the table of lists becoming:
CREATE TABLE Lists (
listID INTEGER PRIMARY KEY,
userID INTEGER,
title TEXT,
comment TEXT,
FOREIGN KEY (userID) REFERENCES Users
);
assuming you have a Users table with primary key userID INTEGER with per-user information (name, etc, etc).
So to get all the lines of a list given its ID you just
SELECT line FROM ListLines
WHERE listID=:whateverid
ORDER BY lineNo;
or you could UNION that with e.g. the title:
SELECT title AS line FROM Lists
WHERE listID=:whateverid
UNION ALL
SELECT line FROM ListLines
WHERE listID=:whateverid
ORDER BY lineNo;
and so on. This flexible and efficient arrangement is the relational way of doing things...

Resources