【问题标题】:How do I change sql 'like' operator dynamically?如何动态更改 sql 'like' 运算符?
【发布时间】:2014-10-29 02:47:34
【问题描述】:

在我的以下代码中,我想动态检索数据库内容。但问题是最终条件。我应该如何改变?

    string qry= "SELECT Data_Sentences FROM table1 Where";
    For(i=0;i<arraylenth;i++)
    {
    qry+= " Data_sentences like '%" + array[i].tostring() + "%' OR";
    }qry += " 1=1";

在此代码中,最终条件 1=1 出错。所有句子检索。我应该如何更改以仅获得预期的句子?

【问题讨论】:

  • 它检索所有内容并不奇怪,因为您正在执行 OR 1=1,在 OR 语句中,如果任何内容为真,则整个语句为真,并且 1==1 始终为真,所以无论以前是什么,你的整个陈述都是真实的
  • @Pienterekaak 是的,谢谢您的解释。我应该在那里添加 1=0。

标签: java mysql sql database oracle11g


【解决方案1】:

改成1=0:

string qry= "SELECT Data_Sentences FROM table1 Where";
For(i=0;i<arraylenth;i++)
{
qry+= " Data_sentences like '%" + array[i].tostring() + "%' OR";
}qry += " 1=0";

当连接器为AND时使用1=1

【讨论】:

  • @Maduri 虽然这可能会提供所需的功能,但它并不能解决明显缺乏理解或代码中明显的其他问题。如果您真的想修复您的代码,我会建议与此(由@JonK)同时提供的更彻底的答案,这将是一个更好的参考。 :) - 上面的代码仍然无法编译。
【解决方案2】:

如果不使用这种有趣的 1=1 或 1=0 虚拟条件会更有意义。

string qry= "SELECT Data_Sentences FROM table1 Where";
For(i=0;i<arraylenth;i++)
{
    qry+= " Data_sentences like '%" + array[i].tostring() + "%'";
    if (i < arraylenth-1)
        qry+= " OR";
}

【讨论】:

  • 虚拟条件的要点是,如果arrayLength 为零,SQL 查询不会处于无效状态。这是很常见的做法,但通常是第一个条件,而不是最后。如果您可以依赖始终存在WHERE 1 = 1 条件,它还允许您不关心是否需要 WHERE 或 AND 如果您动态构建整个查询。
  • 天哪,这就是人们这样做的原因吗?我不时看到这个,但从来不知道。这是搞砸 SQL 的可怕原因。
  • @nablex 我同意,这很难看。但它也比解析整个查询要容易得多,以确定您是否需要添加 AND 或 WHERE(我都经历过)。不管丑不丑,我都会在一周中的任何一天对虚拟条件进行完整解析。
  • 我以编程方式构建了许多 sql,甚至构建了一个 SQL 建模器,它可以输出数百行 SQL。从来没有解析过 SQL 来检查我是否应该添加一些东西。不仅丑陋,而且完全没有必要。
【解决方案3】:

您发布的代码存在一些问题。

  • 循环内的原始String 串联非常糟糕。改用StringBuilder(或StringBuffer,如果需要线程安全)来代替。
  • OR 1 = 1 将始终为真,因此每一行都将满足条件并被返回。

有几个选项可供您选择,以下是其中的一些:

StringBuilder qry = new StringBuilder(
        "SELECT Data_Sentences FROM table1 WHERE 1 = 1");
for (int i = 0; i < array.length; i++) {
    if (i == 0) {
        qry.append(" AND (Data_sentences LIKE '%" + array[i].toString() + "%'");
    } else {
        qry.append(" OR Data_sentences LIKE '%" + array[i].toString() + "%'");
    }

    if (i == array.length - 1) {
        qry.append(")");
    }
}

这个将1 = 1 条件移动到基​​本字符串中,因为无论如何它都会被附加。它还会改变您的 OR 条件的形式,生成如下查询(格式化为便于阅读):

SELECT Data_Sentences
  FROM table1
 WHERE 1 = 1
   AND (Data_Sentences LIKE '%some value%'
        OR Data_Sentences LIKE '%some other value%')

显然,此查询的格式与您原来的格式不同,但功能应该相同。或者,您可以这样做:

StringBuilder qry = new StringBuilder(
        "SELECT Data_Sentences FROM table1 WHERE");
for (int i = 0; i < array.length; i++) {
    qry.append(" Data_sentences LIKE '%" + array[i].toString() + "%' OR");
}
qry.append(" 1 = 0");

这会产生与您当前查询非常相似的内容(再次格式化以方便阅读):

SELECT Data_Sentences
  FROM table1
 WHERE Data_Sentences LIKE '%some value%'
    OR Data_Sentences LIKE '%some other value%'
    OR 1 = 0

我没有执行任何测试来查看哪个查询更有效,但如果我不得不猜测,我会说其中ORs 较少的查询将是两者中的更快,但是差异(如果有的话)可以忽略不计。

第三种选择是首先检查array 的长度,如果它的大小为0,则完全跳过WHERE 子句。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-07-06
    • 1970-01-01
    • 1970-01-01
    • 2021-12-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多