안드로이드에서 DB 작업을 하다보면 다음과 같은 에러를 만날 때가 있다.


"android.database.

       CursorIndexOutOfBoundsException: 

             Index -1 requested, with a size of ..."


이 에러는 DB에서 SELECT한 결과를 Cursor로 받는데 이때 Cursor의 위치가 첫번째 항목 바로 앞(index가 -1인) 위치에 놓이게 된다.

이때 다음 명령을 실행하면 


cursor.getString(cursor.getColumnIndex("name"));


android.database.CursorIndexOutOfBoundsException: Index -1 requested, with a size of 1과 같은 에러가 발생한다.

왜냐하면 cursor의 위치가 before the first entry이기 때문이다. 즉 cursor의 index가 첫 번째 데이터 바로 앞인 -1의 위치에 있기 때문이다.


이건 다음 둘 중 한 방법으로 처리 해야한다.


1) cursor.moveToFirst()를 cursor.getString() 이전에 실행해서 index가 -1인 (첫 번째 항목 바로 앞) 위치에서 첫 번째 항목으로 이동시킨 후

cursor.getString(cursor.getColumnIndex("name"));

과 같은 명령을 통해 원하는 데이터를 추출하면 된다.


2) while문을 이용해서 cursor.moveToNext()를 이용해서 하면 moveToFirst()를 안 해도 된다.

이때 movetToFirst()를 실행하면 맨 첫번째 데이터를 놓치고 넘어가게 된다.

while(cursor.moveToNext()) {...}를 하면 index -1에서 cursor.moveToNext()로 인해

첫 번째 데이터 위치로 index가 옮겨가게 되므로 굳이 moveToFirst()가 필요 없게 된다.


while(cursor.moveToNext()) {

name = cursor.getString(cursor.getColumnIndex("name"));

}


아래는 코드 조각이다.


DBHelper db_Helper = new DBHelper(mContext);

SQLiteDatabase db = db_Helper.getReadableDatabase();

String sql = "SELECT * FROM "+mContext.getString(R.string.memberTable) 

+" WHERE "+mContext.getString(R.string.pinNum)+"='"+pin_num+"';";

//A Cursor object, which is positioned before the first entry.

Cursor cursor = db.rawQuery(sql, null);

//cursor.moveToFirst(); 

if (cursor.getCount() > 0) {

while(cursor.moveToNext()) {

name = cursor.getString(cursor.getColumnIndex("name"));

}

}

db_Helper.close();





안드로이드 SQLite에 대해서 주의해야 할 사항


SQLiteOpenHelp 클래스의 두 abastract 메소드인 onCreate()와 onUpgrade()가 호출되는 시점에 대해서 주의해야 할, 그리고 알아야 할 사항이 있다.

여기서 MyDB는 SQLiteOpenHelper 클래스를 상속받은 클래스라고 할 경우

(class MyDB extends SQLiteOpenHelper)


 MyDB dbHelp = new MyDB(this);

  ⇒ 이 단계에서는 SQLiteOpenHelper를 상속 받은 MyDB의 생성자만 호출이
      되고 MyDB의 onCreate()는 아직 호출이 안된다.


      SQLiteDatabase db = dbHelp.getReadableDatabase() 혹은  
      dbHelp.getWritableDatabase()가 호출 될 때 비로소

      MyDB의 onCreate()가 호출되서 테이블이 생성이 된다. 


      getReadableDatabase()하는 시점에서 테이블이 없으면

      테이블이 새롭게 생성이 되고 기존 존재하면 그것을 Radable이나 Writable 중
      하나로 open한다.


 MyDB의 onUpgrade()가 호출되는 시점

  ⇒ super(context,"Test.db", null, 2); 의 맨 마지막 인자인 DB의
      version 값이 상향 조정될 때 호출된다.




+ Recent posts