Android SQLite checking if tables contain rows - android

So I'm working on a game for android and I'm currently stuck at the 'load savegame' button in the main menu.
This button calls methods that read data from the database and write it into a resource class from which on this data will be accessed.
The problem is: I want to disable the load button if there are no rows in the tables, which means that no savegame exists.
To do this I used the following method:
public boolean checkForTables(){
boolean hasTables;
String[] column = new String[1];
column[0] = "Position";
Cursor cursor;
cursor = db.query("itemtable", column, null, null, null, null, null);
if(cursor.isNull(0) == true){
hasTables=false;
}else{
hasTables=true;
}
return hasTables;
As you can see it starts a query on one of the database tables and checks if the 0-column, which is the only one that should be in this cursor, is null. ATM I can't check logcat results on this call because I seem to have some problems with it, but it seems that the query throws an exception because the table is empty.
Any idea to check the tables for rows?
____________________EDIT______________
NOTE: I checked the database and it sure is empty
Okay I used a rawQuery on the table but the approach with count-statement produced an error, so I'm using
public boolean checkForTables(){
boolean hasTables;
Cursor cursor = db.rawQuery("SELECT * FROM playertable", null);
if(cursor.getCount() == 0){
hasTables=false;
if(cursor.getCount() > 0){
hasTables=true;
}
cursor.close();
return hasTables;
}
I'm using this method to decide whether or not to disable the loadGame-button which looks like this:
loadGame = (ImageButton) findViewById(R.id.loadButton);
loadGame.setEnabled(databaseAccess.checkForTables());
loadGame.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
databaseAccess.loadPlayer();
databaseAccess.loadItems();
databaseAccess.dropTables();
}
});
So if checkForTables gets a rowcount of != 0 it will return true and therefore enable the Button, or disable it if rowcount = 0
Amusingly, although the tables are empty, checkForTables() returns true because getCount() seems to return a != 0 value - I just don't get it.

Perform a query such as select count(*) from itemtable. This query will yield you a single integer result, containing the number of rows in that table.
For example:
Cursor cursor = db.rawQuery("SELECT count(*) FROM itemtable");
if (cursor.getInt(0) > 0) ... // there are rows in the table
-------------------------------------------------------------------------------------
Please note that the following edit was attempted by #PareshDudhat but was rejected by reviewers. I have not kept up with Android since this answer was posted, but a very brief bit of research suggests the edit (at least the change to how rawQuery() is called, I didn't inspect the moveToFirst() but #k2col's comment suggests it is required now as well) has merit.
Cursor cursor = db.rawQuery("SELECT count(*) FROM itemtable",null);
cursor.moveToFirst();
if (cursor.getInt(0) > 0) ... // there are rows in the table

What mah says will work. Another approach you could use in your current function is:
hasTables = cursor.moveToFirst());
Note that this approach is probably only better to use if you plan on using the results of the query if hasTables is in fact true.
Also, don't forget to close your cursor when you are done with it!
EDIT
I don't know if this is your problem but in your edit you are querying for all items from the playerTable instead of the itemTable as you did in the pre-edit. Is that your problem?

cursor.getCount()
return the number of rows in database table.
and then try
Toast.makeText(this,""+cursor.getCount(),Toast.LENGTHLONG).show();
and it will give you no of rows in database table

The accepted answer put me on the right track, but didn't compile because rawQuery's method signature has changed and the cursor wasn't advanced to the first row before being read.
Here's my solution which includes error handling and closes the cursor:
public static boolean isEmpty() {
boolean isEmpty;
Cursor cursor = null;
try {
cursor = db.rawQuery("SELECT count(*) FROM itemtable", null);
if (cursor.moveToFirst()) {
isEmpty = cursor.getInt(0) == 0;
} else {
// Error handling here
}
} catch (SQLException e) {
// Error handling here
} finally {
cursor.close();
}
return isEmpty;
}

Related

What is the significance of closing the cursor in android sqlite?

While reading the sqlite methods to read a row using a cursor I get to know about that after retrieving the data form the cursor we should close the cursor to avoid any memory leak, but here I have a doubt that in the code below cursor.getCount() is called after closing the cursor? Isn't it wrong to retrieve the data after closing the cursor?
Could anyone can clear this doubt!
Thanks in advance!!
public int getContactsCount() {
String countQuery = "SELECT * FROM " + TABLE_CONTACTS;
SQLiteDatabase db = this.getReadableDatabase();
Cursor cursor = db.rawQuery(countQuery, null);
cursor.close();
// return count
return cursor.getCount();
}
Here is the source code for SQLiteCursor#close():
#Override
public void close() {
super.close();
synchronized (this) {
mQuery.close();
mDriver.cursorClosed();
}
}
And here is the source code for SQLiteCursor#getCount():
#Override
public int getCount() {
if (mCount == NO_COUNT) {
fillWindow(0);
}
return mCount;
}
As you can see, the row count appears to be stored in a variable mCount, and this value is not reset when the cursor is closed. This might make sense from an efficiency point of view, since it saves the need to clear out state unnecessarily.
So it appears that getting the count after closing the cursor does work, but you probably should not rely upon it because the Javadoc makes no such guarantees, and this behavior could change later on.
Cursor.getCount()
here in your query i think the code is not wrong because the getcount() method just return the number of rows in the cursor and we are not retrieving any data from the cursor

Checking if the table has rows results in Null Pointer Exception in SQLiite Android [duplicate]

This question already has answers here:
What is a NullPointerException, and how do I fix it?
(12 answers)
Closed 6 years ago.
I want to check if the table has rows and if it contains, then I want to delete it. Below is my code for checking if table has rows in it.
boolean empty = true;
Cursor cursor = db.rawQuery("SELECT count(*) FROM TABLE_NAME",null);
cursor.moveToFirst();
if (cursor.getInt(0) > 0)
{
empty = false;
}
else
{
empty= true;
}
return empty;
I even tried checking with below code,
boolean empty = true;
Cursor cur = db.rawQuery("SELECT COUNT(*) FROM TABLE_NAME", null);
if (cur != null && cur.moveToFirst()) {
empty = (cur.getInt (0) == 0);
}
cur.close();
return empty;
Both of the above code, throws NullPointerException in line
("SELECT COUNT(*) FROM TABLE_NAME", null);
Any help would be great !! Thanks
Android comes with a utility class called DatabaseUtils which has a method queryNumEntries that can take your database object and table name as parameter and return the total number of records on that database. Quite a clean way. You don’t need to be writing ‘Select Count(*) from mytable‘ kind of stuffs.
public long count() {
return DatabaseUtils.queryNumEntries(db,'myTablename');
}
next to delete he rows if your database is not empty try
deleteAll to delete all the rows in dB, or use delete_byID() by passing the ID as parameter to the row which you want to delete.
public int deleteAll(){
return sqLiteDatabase.delete(MYDATABASE_TABLE, null, null);
}
public void delete_byID(int id){
sqLiteDatabase.delete(MYDATABASE_TABLE, KEY_ID+"="+id, null);
}

What is The use of moveToFirst () in SQLite Cursors

I am a programming newbie
and I found this piece of code in the internet and it works fine
Cursor c=db.query(DataBase.TB_NAME, new String[] {DataBase.KEY_ROWID,DataBase.KEY_RATE}, DataBase.KEY_ROWID+"= 1", null, null, null, null);
if(c!=null)
{
c.moveToFirst();
}
but I am not able to understand the use of the
if(c!=null)
{
c.moveToFirst();
}
part. What does it do exactly , and if I remove the
if(c!=null) { c.moveToFirst(); }
part, the code doesn't work.
The docs for SQLiteDatabase.query() say that the query methods return:
"A Cursor object, which is positioned before the first entry."
Calling moveToFirst() does two things: it allows you to test whether the query returned an empty set (by testing the return value) and it moves the cursor to the first result (when the set is not empty). Note that to guard against an empty return set, the code you posted should be testing the return value (which it is not doing).
Unlike the call to moveToFirst(), the test for if(c!=null) is useless; query() will either return a Cursor object or it will throw an exception. It will never return null.
if (c.moveToFirst()) {
while(!c.isAfterLast()) { // If you use c.moveToNext() here, you will bypass the first row, which is WRONG
...
c.moveToNext();
}
}
Cursor is not a Row of the result of query. Cursor is an object that can iterate on the result rows of your query. Cursor can moves to each row. .moveToFirst() method move it to the first row of result table.
moveToFirst() method moves the cursor to the first row. It allows to perform a test whether the query returned an empty set or not. Here is a sample of its implementation,
if (cursor.getCount() == 0 || !cursor.moveToFirst()) {
return cursor.getLong(cursor.getColumnIndexOrThrow(ID_COLUMN));
cursor.close();
what macio.Jun says is right!
we have code like below:
String sql = "select id,title,url,singer,view,info from cache where id=" + id;
SQLiteDatabase db = getMaintainer().getReadableDatabase();
Cursor query = db.rawQuery(sql, null);
query.moveToFirst();
while(query.moveToNext()){
DBMusicData entity = new DBMusicData();
entity.setId(query.getString(query.getColumnIndex(FIELD_ID)));
entity.setTitle(query.getString(query.getColumnIndex(FIELD_TITLE)));
entity.setSinger(query.getString(query.getColumnIndex(FIELD_SINGER)));
entity.setTitlepic(query.getString(query.getColumnIndex(FIELD_PICURL)));
entity.setInfoUrl(query.getString(query.getColumnIndex(FIELD_INFO)));
entity.setViews(query.getString(query.getColumnIndex(FIELD_VIEW)));
Log.w(tag, "cache:"+ entity.toString());
}
query.close();
query=null;
db.close();
db=null;
If we have only one record in the cache table, query.moveToFirst(); will cause that no record returns.

Get updated rows count from SQLite in Android using a raw query?

How can I get the number of rows updated using an update statement in SQLite in Android?
Note that I need to use some type of raw execute of a SQL statement, rather than do anything with ContentValues because I need a dynamic query. Thus I can't make use of the SQLiteDatabase.update() method. For example, I'm running something like
UPDATE my_table
SET field_name = field_name + 1
The methods I know of return void, e.g. SQLiteDatabase.execSQL(). SQLiteDatabase.rawQuery() returns a Cursor, but the cursor has zero rows and its count is always -1.
You could do your insert whichever way you want, and then do a select and use the changes() function to return the number of affected rows.
To expand on Mat's answer, here's the example code for getting the updated row count:
Cursor cursor = null;
try
{
cursor = db.rawQuery("SELECT changes() AS affected_row_count", null);
if(cursor != null && cursor.getCount() > 0 && cursor.moveToFirst())
{
final long affectedRowCount = cursor.getLong(cursor.getColumnIndex("affected_row_count"));
Log.d("LOG", "affectedRowCount = " + affectedRowCount);
}
else
{
// Some error occurred?
}
}
catch(SQLException e)
{
// Handle exception here.
}
finally
{
if(cursor != null)
{
cursor.close();
}
}
Expanding on Mat and Pang's answers...
Could we skip the Cursor and use simpleQueryForLong()?
e.g.
public long getChangesCount() {
SQLiteDatabase db = getReadableDatabase();
SQLiteStatement statement = db.compileStatement("SELECT changes()");
return statement.simpleQueryForLong();
}
You can use SQLiteStatement.executeUpdateDelete method for this:
SQLiteDatabase db = getReadableDatabase();
SQLiteStatement statement = db.compileStatement("[your sql here]");
int affectedRows = statement.executeUpdateDelete();
The same method used internally in SQLiteDatabase.update(...) methods.

SQLite table query

I query the table by using this function below
public Cursor getTableInfo() throws SQLException
{
return db.query(TableName, null,
null,
null,
null,
null,
null);
}
I got the error "View Root.handleMessage(Message)line:1704". I could insert the data but can't query the data. I called this function below
Cursor c = db.getTableInfo();
int cRow = c.getCount();
if (cRow == 0)
{
Toast.makeText(NewContact.this,
"No Record",
Toast.LENGTH_LONG).show();
}
In SQLite, is there any case-sensitive in the name of database, table, column?
Please help me.
Your db request looks ok and it should return all records from your table.
So maybe there are just no records in the table?
Also it's unclear whether you have problem with db related stuff or with smth else, because the code provided looks ok.
I would rather evaluate the outcome of c.moveToFirst() instead of c.getCount(). The latter means the cursor iterates over the whole dataset which is a more costly operation.

Categories

Resources