SQL-запрос: как разбить имя столбца на части (регулярное выражение?) - PullRequest
0 голосов
/ 17 ноября 2010

У меня есть таблица со многими столбцами.Все столбцы (атрибуты) именуются с использованием одного и того же соглашения об именах: thisIsColumnName, thisIsAttributeName, thisIsAlsoColumnName и т. Д. Я хотел бы создать запрос (возможно, используя таблицу information_schema.columns), который разбивает все эти имена на части и создает один список, содержащийотдельные части всех имен столбцов:

thisIsColumnName
thisIsAttributeName

производит

this
Is
Column
Attribute
Name

Как я могу сделать это для всех моих столбцов в таблице (и, возможно, для всех таблиц в базе данных), используя T-SQL?Есть идеи?

Ответы [ 2 ]

1 голос
/ 17 ноября 2010

Один из способов - написать пользовательскую функцию CLR, которая сделала это за вас. Вот пример, где я беру что-то вроде «ThisIsAColumnName» и выдаю «Это имя столбца»

public static String SplitCamel( String input ) {
    return System.Text.RegularExpressions.Regex.Replace(input, "([A-Z][A-Z]*)", " $1", System.Text.RegularExpressions.RegexOptions.Compiled).Trim();
} // method::SplitCamel

См. Это для получения дополнительной информации: http://msdn.microsoft.com/en-us/library/w2kae45k(VS.80).aspx

0 голосов
/ 18 ноября 2010

Как @Chris Lively указывает, что сплошная функция расщепления верблюдов в некоторой форме, вероятно, является лучшим подходом, но вот один запрос, который делает все это встроенным.Очевидно, что здесь сопоставление является соображением для сопоставления с шаблоном, и в этом случае я использовал регистрозависимый в функции PATINDEX (кроме того, мне пришлось явно определять каждую заглавную букву в соответствующем выражении, так как [AZ] не возвращал правильноерезультаты, я думаю, что это тема для другой вопрос ....)

CREATE TABLE dbo.OriginalNames 
(
    CamelCaseName        VARCHAR(30),    
)
GO

INSERT INTO dbo.OriginalNames VALUES ('thisIsColumnName')
INSERT INTO dbo.OriginalNames VALUES ('thisIsAttributeName')
INSERT INTO dbo.OriginalNames VALUES ('thisIsAnotherAttributeName')

GO

SELECT * FROM dbo.OriginalNames;
GO

WITH
L0 AS(SELECT 1 AS c UNION ALL SELECT 1),
L1 AS(SELECT 1 AS c FROM L0 AS A, L0 AS B),
L2 AS(SELECT 1 AS c FROM L1 AS A, L1 AS B),
L3 AS(SELECT 1 AS c FROM L2 AS A, L2 AS B),
Numbers AS(SELECT ROW_NUMBER() OVER(ORDER BY c) AS n FROM L3)
SELECT DISTINCT(SplitNames.Value)
FROM (
SELECT  nums.n, names.CamelCaseName, LTRIM(RTRIM(SUBSTRING(names.CamelCaseName, nums.n - 1, PATINDEX('%[|ABCDEFGHIJKLMNOPQRSTUVWXYZ]%', SUBSTRING(names.CamelCaseName + N'|', nums.n, LEN(names.CamelCaseName)) COLLATE SQL_Latin1_General_Cp1_CS_AS)))) AS [Value]
 FROM   Numbers AS nums INNER JOIN dbo.OriginalNames AS names ON nums.n <= CONVERT(int, LEN(names.CamelCaseName) + 1) AND PATINDEX('%[|ABCDEFGHIJKLMNOPQRSTUVWXYZ]%', SUBSTRING(N'|' + names.CamelCaseName, nums.n, 1) COLLATE SQL_Latin1_General_Cp1_CS_AS) > 0) AS SplitNames

GO

--DROP TABLE dbo.OriginalNames

-- OUTPUT as follows
--
-- Value
-- =========
-- Another
-- Attribute
-- Column
-- Is
-- Name
-- this 
...