How can I expand out a row into multiple row result set?
You can use a recursive CTE:
;WITH CTE AS
(
SELECT *
FROM YourTable
UNION ALL
SELECT id, pcs-1
FROM CTE
WHERE pcs-1 >= 1
)
SELECT *
FROM CTE
ORDER BY id, pcs
OPTION(MAXRECURSION 0)
Here is a demo for you to try.
SQL Server : split one row into many rows (value)
I like using recursive CTEs for this purpose:
with cte as (
select name, name2, 1 as ind, value
from mytable
union all
select name, name, ind + 1, value
from cte
where ind < value
)
select name, name2, 1
from cte
option (maxrecursion 0);
If your data is not too large, then the performance should be fine. If you have large data, then you might want to consider a numbers table.
How can I expand out a row into multiple row result set?
You can use a recursive CTE:
;WITH CTE AS
(
SELECT *
FROM YourTable
UNION ALL
SELECT id, pcs-1
FROM CTE
WHERE pcs-1 >= 1
)
SELECT *
FROM CTE
ORDER BY id, pcs
OPTION(MAXRECURSION 0)
Here is a demo for you to try.
How to split the data in a single row into multiple rows in SQL?
If data type of locationID is varchar then:
create table projects (ProjectID int, LocationID varchar(50));
insert into projects values(1, '[1,2,3,4]');
insert into projects values(2, '[2,3]');
Query:
select projectid, value
from projects
CROSS APPLY STRING_SPLIT(replace(replace(locationid,'[',''),']',''),',')
Output:
projectid | value |
---|---|
1 | 1 |
1 | 2 |
1 | 3 |
1 | 4 |
2 | 2 |
2 | 3 |
How do I expand comma separated values into separate rows using SQL Server 2005?
I arrived this question 10 years after the post.
SQL server 2016 added STRING_SPLIT function.
By using that, this can be written as below.
declare @product table
(
ProductId int,
Color varchar(max)
);
insert into @product values (1, 'red, blue, green');
insert into @product values (2, null);
insert into @product values (3, 'purple, green');
select
p.ProductId as ProductId,
ltrim(split_table.value) as Color
from @product p
outer apply string_split(p.Color, ',') as split_table;
SQL split values to multiple rows
If you can create a numbers table, that contains numbers from 1 to the maximum fields to split, you could use a solution like this:
select
tablename.id,
SUBSTRING_INDEX(SUBSTRING_INDEX(tablename.name, ',', numbers.n), ',', -1) name
from
numbers inner join tablename
on CHAR_LENGTH(tablename.name)
-CHAR_LENGTH(REPLACE(tablename.name, ',', ''))>=numbers.n-1
order by
id, n
Please see fiddle here.
If you cannot create a table, then a solution can be this:
select
tablename.id,
SUBSTRING_INDEX(SUBSTRING_INDEX(tablename.name, ',', numbers.n), ',', -1) name
from
(select 1 n union all
select 2 union all select 3 union all
select 4 union all select 5) numbers INNER JOIN tablename
on CHAR_LENGTH(tablename.name)
-CHAR_LENGTH(REPLACE(tablename.name, ',', ''))>=numbers.n-1
order by
id, n
an example fiddle is here.
Split single row into multiple rows based on Date and time in SQL Server
Below Query will help you.
CREATE TABLE #test
(
Notifications varchar(50)
,StartDate datetime
,EndDate Datetime
,Id int
)
INSERT into #test
select '001003741915','2018-08-20 07:27:00.000','2018-08-21 16:23:00.000',1
UNION select '001003779670','2018-08-21 03:36:00.000','2018-08-21 04:36:00.000',2
UNION select '001003779830','2018-08-21 04:36:00.000','2018-08-21 21:35:00.000',3
UNION select '001003779835','2018-08-21 04:36:00.000','2018-08-24 21:35:00.000',4
;with cte
As ( SELECT
ID,Notifications,StartDate,dateadd(d, datediff(d, 1, StartDate+1), '06:00') as StartOfDay, EndDate,dateadd(d, datediff(d, 1, EndDate+1), '06:00') as EndDayOfDate
FROM #test
)
, Result
AS (
select Id
,Notifications
,StartDate
,CASE WHEN StartOfDay BETWEEN StartDate AND EndDate THEN StartOfDay
WHEN ENDDate <StartOfDay THEN ENDDate
WHEN ENDDate <EndDayOfDate THEN ENDDate
ELSE EndDayOfDate END AS EndDate
from cte
union ALL
Select T.Id
,T.Notifications
,R.EndDate As StartDate
,CASE WHEN R.EndDate+1 < T.EndDate THEN R.EndDate+1 ELSE T.EndDate END AS EndDate
from cte T
INNER JOIN Result R
ON R.Notifications=T.Notifications
WHERE R.EndDate <T.EndDate
)
SELECT * FROM Result order by id
Impala: Split single row into multiple rows based on Date and time
This would be a good spot for a recursive CTE, but unfortunatly Hive does not support those. Here is another aproach, that uses a derived table of numbers to split the periods:
select
t.SrNo,
t.Employee,
greatest(t.startDate, date_add(to_date(t.startDate), x.n)) startDate,
least(t.endDate, date_add(to_date(t.startDate), x.n + 1)) endDate
from mytable t
inner join (select 0 n union all select 1 union all select 2) x
on date_add(to_date(t.startDate), x.n) <= t.endDate
You can expand the subquery to handle more possible periods per row.
Also note that this generates half-open intervals, where the end of the preceding interval is equal to the start of the next one (while in your resultset there is a one minute lag). The logic is that the interval is inclusive on its smaller bound and exclusive on the the outer bound (that way, you make sure to not leave any gap).
Turning a Comma Separated string into individual rows
You can use the wonderful recursive functions from SQL Server:
Sample table:
CREATE TABLE Testdata
(
SomeID INT,
OtherID INT,
String VARCHAR(MAX)
);
INSERT Testdata SELECT 1, 9, '18,20,22';
INSERT Testdata SELECT 2, 8, '17,19';
INSERT Testdata SELECT 3, 7, '13,19,20';
INSERT Testdata SELECT 4, 6, '';
INSERT Testdata SELECT 9, 11, '1,2,3,4';
The query
WITH tmp(SomeID, OtherID, DataItem, String) AS
(
SELECT
SomeID,
OtherID,
LEFT(String, CHARINDEX(',', String + ',') - 1),
STUFF(String, 1, CHARINDEX(',', String + ','), '')
FROM Testdata
UNION all
SELECT
SomeID,
OtherID,
LEFT(String, CHARINDEX(',', String + ',') - 1),
STUFF(String, 1, CHARINDEX(',', String + ','), '')
FROM tmp
WHERE
String > ''
)
SELECT
SomeID,
OtherID,
DataItem
FROM tmp
ORDER BY SomeID;
-- OPTION (maxrecursion 0)
-- normally recursion is limited to 100. If you know you have very long
-- strings, uncomment the option
Output
SomeID | OtherID | DataItem
--------+---------+----------
1 | 9 | 18
1 | 9 | 20
1 | 9 | 22
2 | 8 | 17
2 | 8 | 19
3 | 7 | 13
3 | 7 | 19
3 | 7 | 20
4 | 6 |
9 | 11 | 1
9 | 11 | 2
9 | 11 | 3
9 | 11 | 4
Related Topics
Generated Excel from Ssis But Getting Quote in Every Column
Sequence Doesn't Exist Ora-02289
How to Concatenate Multiple Rows' Fields in a Sap Hana Table
How to Call C# Function in Stored Procedure
Query Running Longer by Adding Unused Where Conditions
MySQL to Get The Count of Rows That Fall on a Date for Each Day of a Month
A Simple SQL Select Query to Crawl All Connected People in a Social Graph
Select The Last Row in a SQL Table
How to Update SQL Table from Excel Directly
Why Does This Oracle Drop Column Alter The Default Value of Another Column
How to Use Group_Concat in Rails
Update Multiple Records in Multiple Nested Tables in Oracle
Get Only Date Without Time in Oracle
Ibm Db2: Generate List of Dates Between Two Dates
How to Add "Weights" to a MySQL Table and Select Random Values According to These