2011-11-16 64 views

回答

288

它通常是当人们建立SQL语句。

当您添加and value = "Toyota"你不必担心是否有之前或刚刚WHERE条件。优化器应该忽略它

没有魔法,只是实际


示例代码:

commandText = "select * from car_table where 1=1"; 

if (modelYear <> 0)  commandText += " and year="+modelYear 
if (manufacturer <> "") commandText += " and value="+QuotedStr(manufacturer) 
if (color <> "")  commandText += " and color="+QuotedStr(color) 
if (california)   commandText += " and hasCatalytic=1" 

否则,你就必须有一组复杂的逻辑:

commandText = "select * from car_table" 
whereClause = ""; 
if (modelYear <> 0) 
{ 
    if (whereClause <> "") 
     whereClause = whereClause + " and "; 
    commandText += "year="+modelYear; 
} 
if (manufacturer <> "") 
{  
    if (whereClause <> "") 
     whereClause = whereClause + " and "; 
    commandText += "value="+QuotedStr(manufacturer) 
} 
if (color <> "") 
{ 
    if (whereClause <> "") 
     whereClause = whereClause + " and "; 
    commandText += "color="+QuotedStr(color) 
} 
if (california) 
{ 
    if (whereClause <> "") 
     whereClause = whereClause + " and "; 
    commandText += "hasCatalytic=1" 
} 

if (whereClause <> "") 
    commandText = commandText + "WHERE "+whereClause; 
+2

太棒了。现在我可以使用字符串而不是数组构建我的复杂查询;)。然而,我确实想用EXPLAIN查询来验证它是否触发了“使用Where”。事实上,事实并非如此。 – landons

+69

尽管更多有经验的程序员会做这样的事'“和”。加入(条件)'来生成WHERE语句...或使用O/RM ... –

+2

如果你正在构建的东西‘或’S,你反而会从“where false”或“where 1 = 0”开始。 –

2

该查询求使1等于1和值等于“TOYOTA”中的所有行。所以在这种情况下它是无用的,但是如果你省略了WHERE语句,使用WHERE 1 = 1来提醒你,你选择了不使用WHERE子句是个好主意。

12

它只是一个永远真实的表达。有些人用它作为解决方法。

他们有一个像静态声明:

select * from car_table where 1=1 

所以他们现在的东西在where子句与

and someother filter 
47

如果该查询被动态构建添加,原作者可能不想要考虑一组空的条件,因此以这样的结尾:

sql = "select * from car_table where 1=1" 
for each condition in condition_set 

    sql = sql + " and " + condition.field + " = " + condition.value 

end 
+24

IMO这只是不好的编码。我个人将所有条件存储在一个数组中,然后用“AND”将它们粘在一起。 – DisgruntledGoat

+3

我相信它更喜欢'“AND”' – V4Vendetta

+12

@DisgruntledGoat - 这绝对是一种更好的做事方式;但是有时候你没有那么容易操作数组和连接语句的好处。 –

30

以及所有其他答案,这是一个简单的技巧SQL injection attacks。如果向某个SQL添加OR where 1=1语句,则由于表达式的固有真实性,它将返回所有结果。

+0

我看不出这与问题有关。无论您有“where 1 = 1 and cond1”还是只有“where cond1”,通过SQLi添加'OR 1 = 1'(我猜OR是哪里出错)将返回所有结果。 –

+4

问题是“1 = 1是什么意思”,我只是认为这将是一个有用的例子来说明如何使用它。 –

+0

我同意这是一个有用的说明。如果有人遇到我为什么看到1 = 1的问题,他们应该始终考虑它是用户制作的SQL注入的可能性。 –

36

1=1永远是真实的,所以value="TOYOTA"位是重要的。

你在几个方案得到这包括:

生成的SQL:它很容易创建出复杂的where声明如果你没有工作,如果你要添加的第一个条件与否,所以往往是一个1=1放在开头,并且所有其他条件可以附加与And

调试:有时候你看到人们把在1=1在WHERE条件上,因为它使他们能够自由地朝令夕改调试查询时的其余条件。例如

select * from car_table 
where 1=1 
--and value="TOYOTA" 
AND color="BLUE" 
--AND wheels=4 

不得不说,它不是特别好的做法,通常不应该在生产代码中出现。它甚至可能无助于查询的优化。

4

1 = 1其中条件始终为真,因为总是1等于1,所以此语句将始终为真。 虽然它有时并不意味着什么。但是其他时候,开发人员在动态生成where条件时使用此选项。

例如,让我们看看这个代码

<?php 
//not that this is just example 
//do not use it like that in real environment because it security issue. 
$cond = $_REQUEST['cond']; 
if ($cond == "age"){ 
$wherecond = " age > 18"; 
}   
$query = "select * from some_table where $wherecond"; 
?> 

所以在上面的例子中,如果$ _REQUEST [“COND”]是不是因为有什么查询将返回MySQL错误“时代”在哪里条件之后。

查询将SELECT * FROM some_table其中,这是错误

来解决此问题(至少在这个不安全的例子),我们使用

<?php 
//not that this is just example 
//do not use it like that in real environment because it security issue. 
$cond = $_REQUEST['cond']; 
if ($cond == "age"){ 
$wherecond = " age > 18"; 
} else { 
$wherecond = " 1=1"; 
}   
$query = "select * from some_table where $wherecond"; 
?> 

所以现在如果$ _REQUEST ['cond']不是年龄 $ wherecond将是1 = 1因此查询将不会有mysql错误返回。

查询将SELECT * FROM some_table其中1 = 1和避免MySQL错误

希望你能明白,当我们使用1 = 1,同时注意上面的例子不是现实世界的例子,它只是为了向你展示这个想法。

+1

您的示例如何成为安全问题?没有可能的SQL注入。安全问题是使用'$ cond'(不将其转换为整数)来指定查询中的最小年龄,并检查isset($ _ REQUEST ['cond'])'是否实际为真(否则使用'1 = 1')。 –

1

当动态传递条件时,此操作的使用会出现在复杂查询中,您可以使用“AND”字符串连接条件。然后,不要计算传递的条件数量,而要在股票SQL语句的末尾放置“WHERE 1 = 1”,并将其放在串联的条件中。

无需使用1 = 1您可以使用0 = 0 2 = 2,3 = 3,5 = 5 25 = 25 ......

select * from car_table where 0=0 and value="TOYOTA" 

在这里你也将得到像1 = 1的条件

相同的结果,因为所有这些情况始终是真实的表达

1=1 is alias for true 
0

我这样做,当我需要动态地应用过滤器。
喜欢,而编码我不知道有多少过滤器用户将申请(fld1 = val1和fld2 = val2和...)
所以,重复语句“和fld = val”我开始“1 = 1”。
因此,我不需要修改声明中的第一个“和”。

4

大多数时间开发的所以随着select语句字符串添加一个条件子句where 1 = 1使用这些类型的查询,如果他正在开发一个查询构建器类型的应用程序或建立一些复杂的SQL查询,并在程序中没有必要添加任何检查。