正则表达式将 sql LIMIT 语法转换为 Sql Server TOP 语法
Regexp convert sql LIMIT syntax to SqlServer TOP syntax
我有一些为 PostgreSQL 编写的查询字符串,我必须将它们转换为 SqlServer。我正在使用 C# 6。
为了将 LIMIT 语法转换为 TOP 语法,我编写了以下简单的正则表达式:
SELECT ([\S\s]*)LIMIT (\d+) -> SELECT TOP
完整的行代码为:
return Regex.Replace(query, @"SELECT ([\S\s]*)LIMIT (\d+)", "SELECT TOP ", RegexOptions.RightToLeft);
现在,一切都适用于简单查询,但不适用于子查询:TOP 字符串每次都放在超级父查询中。
例如尝试以下查询:
SELECT b3.aaa,
b3.count
FROM
(
SELECT CONCAT(b.foo / 100.0, '-', (b.foo + 10) / 100.0) AS aaa,
COUNT(b.foo) AS count
FROM
(
SELECT b2.foo - (b2.foo % 10) AS foo
FROM
(
SELECT CAST(b.foo * 100 AS INT) AS foo
FROM eee b
INNER JOIN bar f ON b.bar_id = f.id
WHERE b.foo < 1
AND f.nome = 'aaa'
) b2
) b
GROUP BY b.foo
ORDER BY b.foo
LIMIT 10
)
转换为:
SELECT TOP 10 b3.aaa,
b3.count
FROM
(
SELECT CONCAT(b.foo / 100.0, '-', (b.foo + 10) / 100.0) AS aaa,
COUNT(b.foo) AS count
FROM
(
SELECT b2.foo - (b2.foo % 10) AS foo
FROM
(
SELECT CAST(b.foo * 100 AS INT) AS foo
FROM eee b
INNER JOIN bar f ON b.bar_id = f.id
WHERE b.foo < 1
AND f.nome = 'aaa'
) b2
) b
GROUP BY b.foo
ORDER BY b.foo
)
虽然我想要
SELECT b3.aaa,
b3.count
FROM
(
SELECT TOP 10 CONCAT(b.foo / 100.0, '-', (b.foo + 10) / 100.0) AS aaa,
COUNT(b.foo) AS count
FROM
(
SELECT b2.foo - (b2.foo % 10) AS foo
FROM
(
SELECT CAST(b.foo * 100 AS INT) AS foo
FROM eee b
INNER JOIN bar f ON b.bar_id = f.id
WHERE b.foo < 1
AND f.nome = 'aaa'
) b2
) b
GROUP BY b.foo
ORDER BY b.foo
)
我应该如何编写我需要的正则表达式?
我为处理引用的括号所做的一些更改可以正常工作:
var pattern = @"SELECT ((?:[^'()]|(?>'[^']+')|(?<open>\()|(?<-open>\)))+(?(open)(?!)))LIMIT (\d+)";
query = Regex.Replace(query, pattern, "SELECT TOP ");
我有一些为 PostgreSQL 编写的查询字符串,我必须将它们转换为 SqlServer。我正在使用 C# 6。
为了将 LIMIT 语法转换为 TOP 语法,我编写了以下简单的正则表达式:
SELECT ([\S\s]*)LIMIT (\d+) -> SELECT TOP
完整的行代码为:
return Regex.Replace(query, @"SELECT ([\S\s]*)LIMIT (\d+)", "SELECT TOP ", RegexOptions.RightToLeft);
现在,一切都适用于简单查询,但不适用于子查询:TOP 字符串每次都放在超级父查询中。
例如尝试以下查询:
SELECT b3.aaa,
b3.count
FROM
(
SELECT CONCAT(b.foo / 100.0, '-', (b.foo + 10) / 100.0) AS aaa,
COUNT(b.foo) AS count
FROM
(
SELECT b2.foo - (b2.foo % 10) AS foo
FROM
(
SELECT CAST(b.foo * 100 AS INT) AS foo
FROM eee b
INNER JOIN bar f ON b.bar_id = f.id
WHERE b.foo < 1
AND f.nome = 'aaa'
) b2
) b
GROUP BY b.foo
ORDER BY b.foo
LIMIT 10
)
转换为:
SELECT TOP 10 b3.aaa,
b3.count
FROM
(
SELECT CONCAT(b.foo / 100.0, '-', (b.foo + 10) / 100.0) AS aaa,
COUNT(b.foo) AS count
FROM
(
SELECT b2.foo - (b2.foo % 10) AS foo
FROM
(
SELECT CAST(b.foo * 100 AS INT) AS foo
FROM eee b
INNER JOIN bar f ON b.bar_id = f.id
WHERE b.foo < 1
AND f.nome = 'aaa'
) b2
) b
GROUP BY b.foo
ORDER BY b.foo
)
虽然我想要
SELECT b3.aaa,
b3.count
FROM
(
SELECT TOP 10 CONCAT(b.foo / 100.0, '-', (b.foo + 10) / 100.0) AS aaa,
COUNT(b.foo) AS count
FROM
(
SELECT b2.foo - (b2.foo % 10) AS foo
FROM
(
SELECT CAST(b.foo * 100 AS INT) AS foo
FROM eee b
INNER JOIN bar f ON b.bar_id = f.id
WHERE b.foo < 1
AND f.nome = 'aaa'
) b2
) b
GROUP BY b.foo
ORDER BY b.foo
)
我应该如何编写我需要的正则表达式?
我为处理引用的括号所做的一些更改可以正常工作:
var pattern = @"SELECT ((?:[^'()]|(?>'[^']+')|(?<open>\()|(?<-open>\)))+(?(open)(?!)))LIMIT (\d+)";
query = Regex.Replace(query, pattern, "SELECT TOP ");