所以我有一张名为“SongsMetadata'在我的数据库中有6列,如下所示(appx 70k记录)。它包含所有与歌曲相关的信息。
与常规数据库表略有不同。 ' File_name'列包含.csv文件。这些是实际的表,它们前面的值是该csv文件中的列。
所以对于' 1001186_1_7562755270480253254.csv'记录在SongsMetadata表中,' 1001186_1_7562755270480253254'是表格名称,它的列是'&#n;',' name',' album',' time', '价格' (这些表包含大量垃圾值)
我的目标是比较所有表(在本例中为.csv文件)以获取所有类似的列名及其计数。现在我已经有了一个解决方案来获取常用列名并计算普通表here。每个表格将与其他表格进行比较。但是,我不确定如何使用.csv表实现相同的效果。
预期输出为:
1001186_1_7562755270480253254.csv & 1001186_0_5503858345485431752.csv |  , name, price| 3 #common columns count
1001186_0_5503858345485431752.csv & 99524146_0_3894874701785592836.csv |  , name, price| 3
and so on...
任何建议都表示赞赏。
答案 0 :(得分:0)
以下解决方案显示了如何处理您的exsting表,以便有效地进行所需匹配。这需要unpivot
,尽管使用cross apply
和{{1}执行了unpivot的效果这是一种简单有效的方法。之后"匹配"显示,然后是另一个查询细节,你也可能觉得有用。最后,显示新表只是为了帮助可视化它是什么。
小样本:
values
UNPIVOT查询
此查询将列信息移动到规范化结构中,以便进行后续匹配。这对整体解决方案至关重要。作为额外的奖励,您可以将一些列名称标记为" bad"以便稍后可以忽略这些,例如CREATE TABLE SongsMetadata
([file_name] varchar(7), [col1] varchar(6), [col2] varchar(6), [col3] varchar(6), [col4] varchar(6))
;
INSERT INTO SongsMetadata
([file_name], [col1], [col2], [col3], [col4])
VALUES
('abc.csv', ' ', 'name', 'price', 'artist'),
('def.csv', 'name', ' ', ' ', 'price')
;
(最有可能是垃圾数据)
查询1 :
这是"匹配逻辑"在http://rextester.com/TLQ28814处提供但适用于不透明的歌曲数据,并且它可以排除您根本不想考虑的列名(col_is_good)。
select
file_name, column_number, column_name
, case when column_name IN (' ','</b>','other-unwanted') then 0 else 1 end as col_is_good
into SongsMetadataUpivot
from (
select file_name, column_number, column_name
from SongsMetadata
cross apply (
values
(1, col1)
, (2, col2)
, (3, col3)
, (4, col4)
) ca (column_number, column_name)
) d
;
<强> Results 强>:
with fmatch as (
select
l.file_name + ' & ' + r.file_name AS comparing_files
, l.column_name
from SongsMetadataUpivot l
inner join SongsMetadataUpivot r on l.column_name = r.column_name
and l.file_name < r.file_name
and r.col_is_good = 1
where l.col_is_good = 1
)
select --* from fmatch
f.comparing_files
, STUFF((
SELECT
N', ' + column_name
FROM fmatch c
WHERE f.comparing_files = c.comparing_files
order by c.column_name
FOR xml PATH (''), TYPE
)
.value('text()[1]', 'nvarchar(max)'), 1, 2, N'') as columns
, count(*) as num_col_matches
from fmatch f
group by f.comparing_files
查询2 :
这将只允许按名称顺序生成列列表以及每个文件中各自的列位置。
| comparing_files | columns | num_col_matches |
|-------------------|-------------|-----------------|
| abc.csv & def.csv | name, price | 2 |
<强> Results 强>:
SELECT
file_name, ca.*
from SongsMetadata f
cross apply (
select
STUFF((
SELECT
N', ' + column_name
FROM SongsMetadataUpivot c
WHERE f.file_name = c.file_name
AND c.col_is_good = 1
ORDER BY column_name
FOR xml PATH (''), TYPE
)
.value('text()[1]', 'nvarchar(max)'), 1, 2, N'')
, STUFF((
SELECT
N', ' + cast(column_number as nvarchar)
FROM SongsMetadataUpivot c
WHERE f.file_name = c.file_name
AND c.col_is_good = 1
ORDER BY column_name
FOR xml PATH (''), TYPE
)
.value('text()[1]', 'nvarchar(max)'), 1, 2, N'')
) ca (column_names, col_numbers)
查询3 :
因此,您可以想象出&#34; unpivoted&#34;数据,整体解决方案需要这样做。
| file_name | column_names | col_numbers |
|-----------|---------------------|-------------|
| abc.csv | artist, name, price | 4, 2, 3 |
| def.csv | name, price | 1, 4 |
<强> Results 强>:
select * from SongsMetadataUpivot