Dynamic sorting by column depending on value in column - sql

Plain and simple: Is it possible to create a dynamic ordering by system, depending on the value inside the column, the query will query.
The query goes something like this:
SELECT id, name, sortbycolumn FROM table
WHERE id = :in_id
UNION
SELECT id, name, null sortbycolumn FROM table
WHERE id = :in_id
ORDER BY -- This part I simply don't know how to write. I have tried case and decode...

To answer. I did finally find the solution. It was quite simple and whilst I read through other answers, I was confused as to why it did not work for me. Apparently the index of a column will not work when using case when.
In the end, I put up the whole query with unions into a subquery with the solution being:
SELECT * FROM(
SELECT id, name, sortbycolumn FROM table
WHERE id = :in_id
UNION
SELECT id, name, null sortbycolumn FROM table
WHERE id = :in_id
)
ORDER BY
case when sortbycolumn = 1 THEN id,
case when sortbycolumn = 2 then name
else id end

Related

SQL - How to get values from multiple tables without being ambiguous

Apologies if this question had been asked before (it probably did). I never used SQL before and the answers I've got only got me more confused.
I need to find out if an ID exists on different tables and get the total number from all tables.
Here is my query:
select * from public.ui1, public.ui2, public.ui3 where id = '123'
So if id 123 doesn't exist in ui1 and ui2 but does exist in ui3, I'd still like to get it. (I would obviously like to get it if it exists in the other tables)
I am currently getting an ambiguous error message as id exists in all tables but I am not sure how to construct this query in the appropriate manner. I tried join but failed miserably. Any help on how to reconstruct it and a stupid proof explanation would be highly appreciated!
EDIT: What I would finally like to find out is if id = 123 exists in any of the tables.
It's a bit unclear what the result is you expect. If you want the count then you can use a UNION ALL
select 'ui1' as source_table,
count(*) as num_rows
from public.ui1
where id = 123
union all
select 'ui2',
count(*)
from public.ui2
where id = 123
union all
select 'ui3',
count(*)
from public.ui3
where id = 123
If you only want to know if the id exists in at least one of the tables (so a true/false) result you can use:
select exists (select id from ui1 where id = 123
union all
select id from ui2 where id = 123
union all
select id from ui3 where id = 123)
What I would finally like to find out is if id = 123 exists in any of the tables.
The best way to do this is probably just using exists:
select v.id,
(exists (select 1 from public.ui1 t where t.id = v.id) or
exists (select 1 from public.ui2 t where t.id = v.id) or
exists (select 1 from public.ui3 t where t.id = v.id)
) as exists_flag
from (values (123)) v(id);
As written, this returns one row per id defined in values(), along with a flag of whether or not the id exists -- the question you are asking.
This can easily be tweaked if you want additional information, such as which tables the id exists in, or the number of times each appears.

Calculate field with value based on select statement

I currently have a select statement which returns Customer Numbers that are primary.
What I would like to do for those returned, I would like to have another column that is for customerRole. For customerRole the value should be either primary or secondary.
My current select statement is bringing those that are primary and based on that select statement. I would like to have a customerRole column that shows these as primary. Then I would like to use this same column with my other select statement to show those that are secondary. When they are ran together I would like to see something like:
accountNumber: 1234455 CustomerRole: Primary
AccountNumber: 3245454 CustomerRole: Secondary
Does anyone know how I can accomplish this? Here is my select to get primary numbers:
SELECT
F.CustomerNumber
FROM ods.CustomerFact F
JOIN ods.holderDim AD
ON F.HolderRowNumber = AD.HolderRowNumber
JOIN ods.holderOwesDim B
ON F.PrimaryHolderNumber = B.SecondaryHolderNumber
I think you want a CASE expression:
SELECT c.CustomerNumber,
(CASE WHEN EXISTS (SELECT 1
FROM ods.holderDim hd
WHERE c.PrimaryHolderNumber = hd.SecondaryHolderNumber
) AND
EXISTS (SELECT 1
FROM ods.holderOwesDim hod
WHERE c.PrimaryHolderNumber = hod.SecondaryHolderNumber
THEN 'Primary' ELSE 'Secondary'
)
END) as role
FROM ods.CustomerFact c;

Determine active rows from multiple tables and place in a Variable Table

I have to determine how many rows are active from each Table. Then return the answers in one query AND put the results in a Table Variable.
a. Path
b. Course
c. Section
d. Event
I was able to determine the active rows with the following query:
SELECT * FROM [dbo].[ADF_Path]
WHERE PathActive is NULL
SELECT * FROM [dbo].[ADF_Course]
WHERE CourseActive = '1'OR
CourseActive = 'y'
SELECT * FROM [dbo].[ADF_Event]
WHERE EventActive = 'y'
Is it POSSIBLE to join these tables in order to arrive at the same conclusion
OR
How do I determine the active rows in 1 query?
Placing the query in a Variable Table is not a problem. I just need to know
how to formulate the query. (See Tables below)
Thank You
do you want something like?:
SELECT count(*) as cnt FROM [dbo].[ADF_Path] WHERE PathActive is NULL
union all
SELECT count(*) FROM [dbo].[ADF_Course] WHERE CourseActive = '1' OR CourseActive = 'y'
union all
SELECT count(*) FROM [dbo].[ADF_Event] WHERE EventActive = 'y'
you can also add column to distinguish between different counts, or summarize them like:
select sum(cnt) from ( <union query from above> ) as t

Get Identity after selecting from distinct result

i have 2 tables ( Model_Table , Items_Table)
Model_Tabl ( ID, ModelName, ModelQuantity)
Items_Tabl ( I_Code, IName, ID)
after inserting new row into (Model_Table) - Triggers insert multi row into (Items_Table) Depend on ModelQuantity from (Model_Table)
, and until now its work fine
I Created "select distinct ModelName , Sum(ModelQuantity) group by ModelName"
and i got result fine
My question is :
When i select model name from (DISTINCT) query i want to know which (ID) I selected from (Model_Table)
Model_ID (TO) Model_Name = 1 (TO) Many
ty
just do:
select ID, ModelName , Sum(ModelQuantity) group by ID, ModelName
as long as ID and ModelName are 1-to-1, you're good.
(Btw, your "distinct" here is superfluous - Select distinct a,b,c from tbl is simply shorthand for Select a,b,c from tbl group by a,b,c)
You have an identity column in the model_table, but you don't appear to be using it in the query where you check the ModelQuantity field. Don't you want to do something like this?
select ModelQuantity
from Model_table
where id = ##identity
?
First of all, you don't need the DISTINCT there, so you can get rid of it. And then, you can try this:
SELECT ID, ModelName, SUM(ModelQuantity) Quantity
FROM Model_Tabl
GROUP BY ID, ModelName
Ok, as I explained on my comment, if you have multiple IDs with the same name, you need to choose one, either the max or the min ID (it still doesn't make sense that you are going to end up just choosing one ID when you actually need to identify that ID), but well, here it is:
SELECT MIN(ID) ID, ModelName, SUM(ModelQuantity) Quantity
FROM Model_Tabl
GROUP BY ModelName

SQL get rows matching ALL conditions

I would like to retrieve all rows matching a set of conditions on the same column. But I would like the rows only if ALL the conditions are good, and no row if only one condition fails.
For example, taking this table:
|id|name|
---------
|1 |toto|
|2 |tata|
I would like to be able to request if "tata" && "toto" are in this table. But when asking if "tata" and "tuto" are in, I would like an empty response if one of argument is in not in the table, for example asking if "toto" && "tutu" are included in the table.
How can I do that ?
Currently, I'am doing one query per argument, which is not very efficient. I tried several solutions including a subselect or a group+having, but no one is working like I want.
thanks for your support !
cheers
This isn't the most efficient way, but this query would work.
SELECT * FROM table_name
WHERE (name = 'toto' OR name = 'tata')
AND ( SELECT COUNT(*) FROM table_name WHERE name = 'toto') > 0
AND ( SELECT COUNT(*) FROM table_name WHERE name = 'tata') > 0
This is a little vague. If the names are unique, you could count the matching rows that match a where clause:
where name='toto' or name='tata'
If the count is 2, then you know both matched. If name is not unique you could potentially select the first ID (select top 1 id ...) that matches each in a union and count those with an outer select.
Even if you had an arbitrary number of names to match, you could create a stored procedure or code in whatever top-level language you are using to build the select statement.
SELECT 1 AS found FROM hehe
WHERE 1 IN (SELECT 1 FROM hehe WHERE name='tata')
AND 1 IN (SELECT 1 FROM hehe WHERE name='toto')
If name is unique you can simplify to:
SELECT *
FROM tbl
WHERE name IN ('toto', 'tata')
AND (SELECT count(*) FROM tbl WHERE name IN ('toto', 'tata')) > 1;
If it isn't:
SELECT *
FROM tbl
WHERE name IN ('toto', 'tata')
AND EXISTS (SELECT * FROM tbl WHERE name = 'toto')
AND EXISTS (SELECT * FROM tbl WHERE name = 'tata');
Or, in PostgreSQL, MySQL and possibly others:
SELECT *
FROM tbl
WHERE name IN ('toto', 'tata')
AND (SELECT count(DISTINCT name) FROM tbl WHERE name IN ('toto', 'tata')) > 1;