2012-11-12 12 views
4

(당신은 더 나은 뭔가 생각할 수있는 경우에 질문 제목을 개선하시기 바랍니다.)이상한 행동

질문 :

SELECT COUNT(*) 
    FROM (SELECT 1 AS value UNION SELECT 2 AS value) 
WHERE value <= ? 

다음 SQLite는 쿼리를 살펴 나는 1을 매개 변수로 사용하며, 1을 산출하는 쿼리를으로 기대하지만 아직 2을 산출합니다. 왜 이런 일이 생길까요?


추가 정보 :

Cursor c = db.rawQuery(
     "SELECT COUNT(*) " + 
     " FROM (SELECT 1 AS value UNION SELECT 2 AS value) " + 
     " WHERE value <= ? ", 
     new String[] {String.valueOf(1)}); 

c.moveToFirst(); 
Log.i("", "Result: " + String.valueOf(c.getInt(0))); 

그것은 사실 매개 변수가 함께 할 수있다 :

이이 문제 (안드로이드)을 재현 할 수있는 최소한의 일 예이다 문자열로 전달되지만, 아, SQLite API에 매개 변수를 전달할 수있는 다른 방법이 없으므로 여기서는 "잘못된"것은 아니며 ap 값을 변환하는 것은 SQLite의 작업입니다 독점적으로. 내가 관찰 한 쿼리의 매개 변수가없는 버전 (이 또는 문제에 대한 관련되지 않을 수도 있습니다)를 사용할 때 다음

SELECT COUNT(*) 
    FROM (SELECT 1 AS value UNION SELECT 2 AS value) 
WHERE value <= 1    -- yields 1 

SELECT COUNT(*) 
    FROM (SELECT 1 AS value UNION SELECT 2 AS value) 
WHERE value <= '1'   -- yields 2 
+0

이 적합합니다. char '1'= 49 – njzk2

+0

당신은 SELECT '1'과 SELECT '2'를 사용할 수 있습니다 – njzk2

답변

5

그것은이 rawQuery 문서에서 말했다 것 :

을 [...] 질의에 where 절을 포함 할 수 있습니다.이 절은 selectionArgs의 값으로 대체됩니다. 값은 문자열로 바인딩됩니다.

비교 한 결과는 다음과 같은 규칙에 따라 피연산자의 스토리지 클래스에 의존 [...]

그리고 INTEGER 또는 REAL 값은 TEXT 또는 BLOB 값보다 작습니다. 정수는

(1) 모두로, 2, 그들은 '1'(TEXT 값)보다 두 이하입니다.

SELECT 2 <= '1' 

... SQLite는 1을 반환이 사항이 이유입니다. 대신

당신은 아마 사용해야합니다 ...

WHERE value <= CAST('1' AS INTEGER) 

.... 또는 모든 수학 연산자가 두 피연산자를 모두 WHERE value <= + ?이라는 숫자의 저장소 클래스로 캐스팅한다는 사실을 사용할 수 있습니다. 그러나 이것은 덜 깨끗합니다._id가 숫자 인 경우 따라서 그들은 숫자로 비교합니다 -

SELECT * FROM myTable WHERE _id < ? 

... the value of ? will get its affinity adjusted to the affinity of _idcolumn이 :이 쿼리에 있음을

참고.

+1

그건 고마워요! 따라서 매개 변수의 자동 유형 조정은 데이터베이스 열과 직접 비교할 때만 작동합니다. 알아두면 좋습니다. – Heinzi