Trigger to sort and update table in SQL Server - sql

I have a table like this, Id is the primary key, so obviously the tables is ordered by Id.
+----+----------+--------+
| Id | OrderNo | Col2 |
+----+----------+--------+
| 1 | 3 | Value3 |
| 2 | 1 | Value1 |
| 3 | 2 | Value2 |
+----+----------+--------+
What I want to do is to reorder the table after every new insert by OrderNo, as follows:
+----+----------+--------+
| Id | OrderNo | Col2 |
+----+----------+--------+
| 2 | 1 | Value1 |
| 3 | 2 | Value2 |
| 1 | 3 | Value3 |
| 4 | 4 | Value4 |
+----+----------+--------+
Is this possible? I looked at this question, It says to drop and re-create the table. Is there anyway that i can do it with one go?
As a matter of fact I tried to execute the first query in the accepted answer but SSMS gives me an error.

Use a view to have the data sorted in any manner you like independent of what has been input.

Related

SQL Count number of column based on another column

Simple question here but I don't have any data to test with so I'm not sure if it is right.
Let's say I have a table that looks something like this:
+---------+---------+
| ColumnA | ColumnB |
+---------+---------+
| 1 | a |
| 2 | a |
| 3 | a |
| 3 | b |
| 4 | a |
| 5 | a |
| 6 | a |
| 6 | b |
| 6 | c |
| 7 | a |
+---------+---------+
I want to count the number of distinct items in column b for each column a.
So the result table would look like this:
+---------+---------+
| ColumnA | Count |
+---------+---------+
| 1 | 1 |
| 2 | 1 |
| 3 | 2 |
| 4 | 1 |
| 5 | 1 |
| 6 | 3 |
| 7 | 1 |
+---------+---------+
How would I do this?
I've been trying something like this:
dense_rank() over (partition by ColumnA order by ColumnB) count
You can use GROUP BY and COUNT with DISTINCT:
SELECT ColumnA, COUNT(DISTINCT ColumnB) AS [Count]
FROM MyTable
GROUP BY ColumnA
demo on dbfiddle.uk

SQL Concat Id column with another column

Here is what I want to do:
I have this table
+----+-------------+
| id | data |
+----+-------------+
| 1 | max |
| 2 | linda |
| 3 | sam |
| 4 | henry |
+----+-------------+
and I want to Update the data with concatenating Id column with data, which will look like this:
+----+-------------+
| id | data |
+----+-------------+
| 1 | max1 |
| 2 | linda2 |
| 3 | sam3 |
| 4 | henry4 |
+----+-------------+
Sounds like this is basically what you want (T-SQL, Other platforms may have different methods for type conversion and concatenation):
update myTable
set data=data+convert(varchar(50),id)

Liquibase script to delete table element based on other table element

I am pretty unfamiliar with liquibase script.
I have two tables, tableA and tableB.
tableB contains elements that have a tableA_fk value. It means that they point to an element of tableA.
tableA contains elements that come always by group of two. One of the element point to the pk of the other element (relatedpk).
I want to delete all the elements of the tableA that have the field "someValue" equal to NULL and no element of tableB pointing to it.
The elements can be removed only by group of two
Example:
tableA:
+----+---------------------+-----------+-----------+
| pk | name | someValue | relatedpk |
+----+---------------------+-----------+-----------+
| 1 | ElementA | 1 | NULL |
| 2 | ElementA | 1 | 1 |
| 3 | ElementB | NULL | NULL |
| 4 | ElementB | NULL | 3 |
| 5 | ElementC | 3 | NULL |
| 6 | ElementC | 3 | 5 |
| 7 | ElementD | NULL | NULL |
| 8 | ElementD | NULL | 7 |
| 9 | ElementE | NULL | NULL |
| 10 | ElementE | NULL | 9 |
+----+---------------------+-----------+-----------+
tableB:
+----+------------------------------+-----------+
| pk | name | tableA_fk |
+----+------------------------------+-----------+
| 1 | Value1 | 2 |
| 2 | Value2 | 3 |
| 3 | Value3 | 9 |
+----+------------------------------+-----------+
In this example I want to remove ElementD with pk=7,8 from tableA.
Reason:
ElementA cannot be removed because
someValue != null
ElementB cannot be removed because
tableA_fk = 3 for element Value2 in tableB
ElementC cannot be removed because
someValue != null
ElementD can be removed because
someValue=NULL
No Element from tableB point to one of this two elements from tableA.
ElementE cannot be removed because
tableA_fk = 9 for element Value3 in tableB
Is it possible to implement somthing like that in a liquibase script?
In something like that
<changeSet id="remove-elements">
<delete tableName="tableA">
<where>ConditionToRemoveTheCorrectELements</where>
</delete>
</changeSet>
Rather than trying to use the <delete tableName> tag, I would suggest that you just write the SQL required and use a <sql> or <sqlFile> change tag.

Create a combined list from two tables

I have a table with CostCenter_ID (int) and a second table with Process_ID (int).
I'd like to combine the results of both tables so that each cost center ID is assigned to all process IDs, like so:
|CostCenterID | ProcessID |
---------------------------
| 1 | 1 |
| 1 | 2 |
| 1 | 3 |
| 2 | 1 |
| 2 | 2 |
| 2 | 3 |
| 3 | 1 |
| 3 | 2 |
| 3 | 3 |
I've done it before but I'm drawing a blank. I've tried this:
SELECT CostCenter_ID,NULL FROM dbo.Cost_Centers
UNION ALL
SELECT NULL,Process_ID FROM dbo.Processes
which returns this:
|CostCenterID | ProcessID |
---------------------------
| 1 | NULL |
| NULL | 1 |
| NULL | 2 |
| NULL | 3 |
Try:
select a.CostCenterID, b.ProcessID
from table1 a
cross join table2 b
or:
select a.CostCenterID, b.ProcessID
from table1 a
,table2 b
NB: cross join is the better method as it makes it clearer to the reader what your intentions are.
More info (with pics) here: http://www.w3resource.com/sql/joins/cross-join.php

Selecting values from a table where values from one column is divided into multiple columns

I'm trying to develop a query in which the values of a single column are split into two or more separate columns to reflect whether or not a particular id has each of the different values.
For example, I have a table like this:
------------
| id | Val |
|----|-----|
| 1 | A |
| 1 | B |
| 2 | A |
| 3 | A |
| 4 | B |
| 5 | A |
------------
The query would produce a table that looks like this:
----------------------
| id | Val_1 | Val_2 |
|----|-------|-------|
| 1 | A | B |
| 2 | A | |
| 3 | A | |
| 4 | | B |
| 5 | A | |
----------------------
Specifically, I would like this query to show only id's that have missing values (i.e. id "1" would be knocked off the table).
So far I have tried this by using a self inner join, but I have not been able to find the select WHERE clauses to produce this.
Any Suggestions?
Thanks!
Update : filtering out columns that have Val_1 and Val_2
SELECT * FROM
(
SELECT id, MAX(CASE WHEN val='A' THEN 'A' END) as Val_1,
MAX(CASE WHEN val='B' THEN 'B' END) as Val_2
FROM table1 GROUP BY id
)a
WHERE Val_1 IS NULL OR Val_2 IS NULL;