是否可以转换表的条目并将其存储到SQL Server的临时表中?

时间:2017-04-28 07:20:00

标签: c# sql sql-server

我想从我的表中转移数据并对powerBI做一些绘图。

以下是我从应用程序中感受数据库的方式:

using (SqlCommand cmd = connect.CreateCommand())
{
    cmd.CommandText = @"INSERT INTO PoD_NewPriceList_Data
                                        (ID, Product_Barcode, Product_Name,
                                         Store_Price, Internet_Price, InsertDate)
                        VALUES (@ID, @Product_Barcode, @Product_Name,
                                @Store_Price, @Internet_Price, @InsertDate)";

    cmd.Parameters.Add("Product_Barcode", SqlDbType.NVarChar).Value = barcode;
    cmd.Parameters.Add("Product_Name", SqlDbType.NVarChar).Value = PriceList.name;
    cmd.Parameters.Add("Store_Price", SqlDbType.Float).Value = Convert.ToDouble(storePrice, CultureInfo.InvariantCulture);
    cmd.Parameters.Add("Internet_Price", SqlDbType.Float).Value = Convert.ToDouble(PriceList.price, CultureInfo.InvariantCulture);
    cmd.Parameters.Add("InsertDate", SqlDbType.DateTime).Value = InsertDate.AddDays(2);
    cmd.Parameters.Add("ID", SqlDbType.Int).Value = barcode.GetHashCode();

    result = result && (cmd.ExecuteNonQuery() > 0);
}

在SQL Server Management Studio中,我的表格如下:

SELECT 
    [ID], [Product_Barcode], [Product_Name],
    [Store_Price], [Internet_Price], [InsertDate]
FROM 
    [dbo].[PoD_NewPriceList_Data]

我得到以下输出:

enter image description here

主要问题是当尝试按照PowerBI中的要求创建绘图时,我需要将数据看起来如下:

                    F5321
    Product_Name    Sony Xperia...
    Store_Price     399
    Internet_Price  327.51
    InsertDate      2017.04.27

任何帮助都将受到赞赏。

1 个答案:

答案 0 :(得分:1)

检查并修改此SQL脚本。我使用@t表变量,将其替换为您的表名[PoD_NewPriceList_Data]

DECLARE @t TABLE (
id int,
product_barcode varchar(max),
product_name varchar(max),
store_price int,
internet_price decimal,
insert_date date
)

INSERT INTO @t VALUES (1,'F5321', 'Sony Xperia', 399, 255.1, '2017-04-25')
INSERT INTO @t VALUES (2,'F5833', 'Sony Xperia XZ', 458, 398.2, '2017-04-26')
INSERT INTO @t VALUES (3,'F5121', 'Sony Xperia XA Rose', 161, 155.6, '2017-04-27')

IF OBJECT_ID ('tempdb..#Unpivoted') IS NOT NULL
   DROP TABLE #Unpivoted
IF OBJECT_ID ('tempdb..#Transposed') IS NOT NULL
   DROP TABLE #Transposed

/* Unpivot table to get rows instead of columns */
SELECT *, ROW_NUMBER() OVER (ORDER BY (SELECT 0)) as rn
INTO #Unpivoted
FROM (SELECT product_barcode, product_name, 
      CAST(store_price as varchar(max))  store_price,
      CAST(internet_price as varchar(max))  internet_price, 
      CAST(insert_date as varchar(max)) as insert_date
      FROM @t) src
UNPIVOT (
    value FOR field IN (
        product_barcode, product_name, store_price, internet_price, insert_date
    )
) unpiv

CREATE TABLE #Transposed 
(Field varchar(50) PRIMARY KEY NOT NULL )

DECLARE @SQL NVARCHAR(MAX)
SELECT @SQL = STUFF((
    SELECT 'ALTER TABLE #Transposed ADD item' + 
    RIGHT('000' + CAST(sv.number AS VARCHAR(3)), 3) + ' varchar(max) '
    FROM [master].dbo.spt_values sv
    WHERE sv.[type] = 'p'
        AND sv.number BETWEEN 1 AND (SELECT COUNT(*) FROM @t)
    FOR XML PATH(''), TYPE).value('.', 'NVARCHAR(MAX)'), 1, 0, '') 

Exec(@SQL)  /* Dynamically create columns */

INSERT INTO #Transposed (Field)  SELECT DISTINCT Field FROM #Unpivoted 
/*populate field names*/
DECLARE @fieldCount int = (SELECT COUNT(*) FROM #Transposed)

/* using rn to filter proper record from transposed table */
SELECT @SQL = STUFF((
    SELECT '
    UPDATE #Transposed SET item' + RIGHT('000' + CAST(sv.number AS VARCHAR(3)), 3) 
    + ' = up.value FROM #Transposed t  CROSS APPLY 
    ( SELECT TOP 1 u.value FROM  #unpivoted u WHERE u.field = t.field AND u.rn > ' 
    + CAST((sv.number-1)*@fieldCount AS VARCHAR(10)) + ' ORDER BY rn) up  '
      FROM [master].dbo.spt_values sv
      WHERE sv.[type] = 'p'
        AND sv.number BETWEEN 1 AND (SELECT COUNT(*) FROM @t)
      FOR XML PATH(''), TYPE).value('.', 'NVARCHAR(MAX)'), 1, 0, '') 

Exec(@SQL)  /*Dynamically fill in values */

SELECT t.* FROM #Transposed t 
OUTER APPLY (SELECT TOP 1 rn FROM #Unpivoted u WHERE u.field=t.field) up
ORDER BY up.rn ASC  /* add a link to Unpivoted to fix the item order */

DROP TABLE #Unpivoted
DROP TABLE #Transposed

它可以通过几个步骤完成您的需要

  1. 将列转换为UNPIVOT的行。注意您必须将所有值CAST到完全相同的类型。添加行号以在步骤3中过滤行。
  2. 创建一个临时表,其动态列数对应于行数
  3. 将列名填充到动态创建的表中
  4. 将值填入动态创建的表格
  5. this answerthis answer

    当然列数有限,所以如果你尝试将很多行转换成列,你会得到:

      

    无法创建大于8066的行,该行大于允许值   最大行数为8060。