Sorting Middle string - sql

I have the following values in a column
Name
Smith
Marry
Tom
Robert
Albert
I have to display in the following order. I want MARRY on top. For the rest of the values ordering is not matter.
Name
Marry
Smith
Tom
Robert
Albert
How can I achieve this?

You can use case in order by:
order by (case when name = 'Marry' then 1 else 2 end)

Related

SQL count in a table

I'm looking to add some form of count function to my table, but am not quite sure how to do it. The table I have is:
First name
Surname
Tom
James
Mike
James
Tom
James
Mike
Hamilton
William
Morris
Mike
James
Mike
James
I would like it to have a count, of the full names that come up twice or more, like so:
First name
Surname
Count
Tom
James
1
Mike
James
1
Tom
James
2
Mike
Hamilton
1
William
Morris
1
Mike
James
2
Mike
James
3
What is the best way to go about this in SQL? Unfortunately I need the result as per the table above, rather than simply:
First name
Surname
Count
Tom
James
2
Mike
James
3
Mike
Hamilton
1
William
Morris
1
row_number function should work
select *,
row_number() over(partition by [first name],surname order by [first name]) as count
from table_name
I believe using group by on multiple columns would be a more appropriate approach to
select [first name], surname, COUNT(*) from Employee Group BY [first name], surname;
I believe using group by on multiple columns would be a more appropriate approach to
select [first name], surname, COUNT(*) from Employee Group BY [first name], surname;
Result:

How to sort in PostgreSQL by uppercase first and after by alphabetically?

When I query database with:
select *
from users
order by name
results are like this:
Adam
AVA
adrian
James
JESSICA
John
I would like to have rows in order like:
rows with all uppercase
rows with first letter or more uppercase
rows alphabetically
Example:
AVA
JESSICA
Adam
James
John
adrian
But anyway for me will be enough to:
AVA
JESSICA
Adam
adrian
James
John
This can be done by using CASE WHEN and testing uppercase;
SELECT *,
CASE
WHEN name = UPPER(name) THEN 1
WHEN LEFT(name, 1) = UPPER(LEFT(name, 1)) THEN 2
ELSE 3
END toOrder
FROM users
ORDER BY toOrder, name ASC
Tested on PostgreSQL 13

Detect duplicate string or word in a row

I want to know how to detect duplicate word in a row. This is to ensure that we have clean data in our database.
For example see below
Name count
James James McCarthy 1
Donald Hughes Hughes 1
I want the result to be like
Name count
James McCarthy 1
Donald Hughes 1
Is there a solution to this using Oracle SQL?
For adjacent words
select 1
from dual
where regexp_like ('John John Doe','(^|\s)(\S+)\s+\2(\s|$)')
;
or
select case when regexp_like ('John John Doe','(^|\s)(\S+)\s+\2(\s|$)') then 'Y' end as adj_duplicate
from dual
;

pl/sql query to remove duplicates and replace the data

I have the following table:
data_id new_data_id first_name last_name
1 john smith
2 john smith
3 john smith
4 jeff louis
5 jeff louis
6 jeff louis
The above table has duplicate first and last names, and the data_id is different for all of them. In order to remove these duplicates, I would need to write a SQL query to replace the highest data_id in new_data_id column. My output would look something like this:
data_id new_data_id first_name last_name
1 3 john smith
2 3 john smith
3 3 john smith
4 6 jeff louis
5 6 jeff louis
6 6 jeff louis
How would I do this?
What you're looking for is an Oracle analytic function.
The aggregate function MAX can be used to select the highest data_id from your entire resultset, but that's not exactly what you need. Instead, use its alter ego, the MAX analytic function like so:
SELECT
data_id,
MAX(data_id) OVER (PARTITION BY first_name, last_name) AS new_data_id,
first_name,
last_name
FROM employees
ORDER BY data_id
This works by "partitioning" your resultset by first_name and last_name, and then it performs the given function within that subset.
Good luck!
Here's a fiddle: http://sqlfiddle.com/#!4/48b29/4
More info can be found here:
http://docs.oracle.com/cd/E11882_01/server.112/e41084/functions004.htm#SQLRF06174
If you need a change in place, a correlated update is probably the simplest way to write that:
UPDATE T
SET "new_data_id" =
(SELECT MAX("data_id") FROM T T2
WHERE T2."first_name" = T."first_name"
AND T2."last_name" = T."last_name")
See http://sqlfiddle.com/#!4/51a69/1

How Do I Exclude Data Based on Column Values in SQL?

I have a table which is set up like this:
Name QuestionCd Response
John Smith 837987 3
John Smith 837988 NULL
John Smith 837991 3
John Smith 837996 3
John Smith 838003 NULL
Mary Smith 837987 1
Mary Smith 837988 1
Mary Smith 837991 3
Mary Smith 837996 1
Mary Smith 838003 5
I need to bring in the customer who has a response for all 5 questions, which would be Mary Smith. I've tried to use a case statement to flag the rows that have a response but that would be incorrect since John Smith did not answer all of the questions.
I've tried the following:
-- Case when QuestionCd between '837987' and '838069' and response is null then '' else 'X' end
-- Case when QuestionCd between '837987' and '838069' and Response is null then ''
when QuestionCd between '837987' and '838069' and Response is not null then 'x' end
Any ideas or tips on how to accomplish this? Thank you kindly for your help.
This is how I would do it.
SELECT Name
FROM
(
SELECT Name, QuestionCd
FROM <YourTable>
WHERE NOT Response IS NULL
GROUP BY Name, QuestionCd
) SQ
GROUP BY Name
HAVING COUNT(QuestionCd)=5
The sub query is to have a distinct list of question answered since Mary Smith or John Smith may have answered the question more than one.
If the question ID's are fixed you can just return the name of the person who has answered 5 unique questions
SELECT Name FROM tbl
GROUP BY Name
HAVING count(QuestionCD) = 5
Edit - fixed SQL