我有一个包含 sql 命令的字符串,
像这样的东西:
strCommand = "Select [Feild1], [Feild2] From TableName Order By [Feild1] desc" ;
如何在这个字符串中找到表名?
我有一个包含 sql 命令的字符串,
像这样的东西:
strCommand = "Select [Feild1], [Feild2] From TableName Order By [Feild1] desc" ;
如何在这个字符串中找到表名?
到目前为止,解决方案都采用了在字符串中搜索的方法。您还没有提到您的 SQL 查询是否总是看起来相似,但是有许多查询变体可以包含这些解决方案将中断的内容。考虑...
SELECT Field1, Field2 FROM TableName
SELECT Field1, Field2 FROM [TableName]
SELECT Field1, Field2 FROM dbo.TableName
SELECT Field1, Field2 FROM Table1Name, Table2Name
如果您尝试解析的查询是您拥有数据库的查询,您可以让 SQL Server 为您完成解析查询的艰苦工作,而不是尝试考虑 SQL 中的所有情况。您可以使用 执行查询SET SHOWPLAN_ALL ON
,这将生成查询计划表。然后,您可以分析 Arguments 列,其中包含标准格式的查询将涉及的所有字段。下面是一个示例程序:
SqlConnection conn = new SqlConnection(CONNECTIONSTRING);
conn.Open();
SqlCommand cmd = conn.CreateCommand();
cmd.CommandText = "SET SHOWPLAN_ALL ON";
cmd.ExecuteNonQuery();
cmd.CommandText = "SELECT [Field1], [Field2] FROM [TableName]";
DataTable dt = new DataTable();
dt.Load(cmd.ExecuteReader());
Regex objectRegex = new Regex(@"^OBJECT:\(\[(?<database>[^\]]+)\]\.\[(?<schema>[^\]]+)\]\.\[(?<table>[^\]]+)\]\.\[(?<field>[^\]]+)\]\)$", RegexOptions.ExplicitCapture);
List<string> lstTables = new List<string>();
foreach (DataRow row in dt.Rows)
{
string argument = row["Argument"].ToString();
if (!String.IsNullOrEmpty(argument))
{
Match m = objectRegex.Match(argument);
if (m.Success)
{
string table = m.Groups["schema"] + "." + m.Groups["table"];
if (!lstTables.Contains(table))
{
lstTables.Add(table);
}
}
}
}
Console.WriteLine("Query uses the following tables: " + String.Join(", ", lstTables));
这将处理所有形式的查询名称并返回查询中涉及的所有表,无论它们是如何包含的。
如果这一直是相同的模式,那么:
string tableName = strCommand.Split(' ', strCommand)[4];
但是如果您可以添加/删除字段,只需遍历拆分的字符串并搜索“From”,下一个字符串将是您的表名
我会说 - “From”之后的内容是一种更可靠的获取表名的方式。遍历创建的数组,当您到达“From”时,下一个是表格。
这是为我们提供表名的方法,只需更改 SQL 查询字符串、连接字符串
适用于简单查询,也可以连接
public static List<string> getTablenames(string connString, string QueryString)
{
SqlConnection con = new SqlConnection(connString);
con.Open();
DataTable dt = con.GetSchema("Tables");
List<string> getTableName = new List<string>();
List<string> tablenames = new List<string>();
foreach (DataRow dr in dt.Rows)
tablenames.Add(dr[2].ToString());
for (int i = 0; i < dt.Rows.Count; i++)
{
string myTable = tablenames[i];
Boolean checkMyTable = QueryString.Contains(myTable);
if (checkMyTable == true)
getTableName.Add(myTable);
}
con.Close();
return getTableName;
}
您可以使用子字符串(这样,您必须选择多少列都没有关系)
string table = strCommand.ToLower().Substring(strCommand.IndexOf("FROM".ToLower())).Split(' ')[0];
ISun 的回答满足了我的需求,但需要进行一项更改才能获取表名:
string table = strCommand.ToLower().Substring(strCommand.IndexOf("FROM".ToLower())).Split(' ')[1];
不是
string table = strCommand.ToLower().Substring(strCommand.IndexOf("FROM".ToLower())).Split(' ')[0];
如果你想要 SQL 的解决方案,试试这个
declare @q varchar(1000) = 'Select [Feild1], [Feild2] From TableName Order By [Feild1] desc',
@tableName varchar(100) = '',
@temp varchar(1000),
@temp2 char(1)
declare @frmIndex int = CHARINDEX('From', @q, 0);
declare @flag int = 0, @counter int = 1;
select @temp = SUBSTRING(@q, @frmIndex, len(@q))
set @temp = LTRIM(REPLACE(@temp,'From',''))
while(@flag <> 1)
begin
set @temp2 = SUBSTRING(@temp, @counter, 1)
if(@temp2 = ' ')
set @flag = 1
select @tableName = @tableName + @temp2
set @counter = @counter + 1
end
select @tableName as TableName