I'm having a lot of trouble with checking if a cursor contains any results.
I have a method that "removes" all rows from a given table which is here:
Chevron.class
public void deleteAllRecords(){
SQLiteDatabase db = this.getWritableDatabase();
db.delete(TABLE_NAME,null,null);
}
I then call a method which adds the SUM of the first row of the database which is here:
public Cursor getRecalculate(){
SQLiteDatabase db = this.getWritableDatabase();
Cursor res = db.rawQuery("select SUM (" + SECOND_FIELD + ") FROM " + TABLE_NAME, null);
return res;
}
My major issue is that if I remove all records from the database, res.getCount() still equals 1 but contains no information but then the method only returns 1 row anyway. So I'm stuck with how to check if the cursor has actual table data or just empty table data.
I've tried stuff like
if(res.getString(0) == null){
.. Do code
}
but that doesn't work.
I get the error:
java.lang.RuntimeException: Unable to start activity ComponentInfo{com.example.ceri.twostep_onecheck/com.example.ceri.twostep_onecheck.ShowGraph}: android.database.CursorIndexOutOfBoundsException: Index -1 requested, with a size of 1
If you want to know how many rows there are that match your query constraints, add COUNT(*) to the SELECT statement:
SELECT COUNT(*), SUM(whatever) FROM other_thing;
Then, move the Cursor to the first row via moveToFirst(), and examine the two values (getInt(0) for the count and getInt(1) for the sum).
Use getReadableDatabase() instead of getWritableDatabase().
Try this:
public Cursor getRecalculate() {
SQLiteDatabase db = this.getReadableDatabase();
Cursor res = db.rawQuery("select SUM (" + SECOND_FIELD + ") FROM " + TABLE_NAME, null);
return res;
}
Read cursor value:
// Move the cursor to the first row if cursor is not empty
if(res.moveToFirst())
{
do
{
// Do something with cursor
}while(res.moveToNext()); // Move cursor to next row until it pass last entry
}
// Close
res.close();
Hope this will help~
Try this
cursor.getCount();
This should return at least one if cursor reads something or it will return zero.
Related
My Cursor is always -1 when i send a request to my database (sqlite) to load an image.
public Cursor getData(int id){
SQLiteDatabase db = this.getWritableDatabase();
String query = "SELECT * FROM " + TABLE_NAME + " WHERE ID = " + id;
Log.d(TAG, query);
Cursor data = db.rawQuery(query, null);
return data;
}
The result is an app crash and this log in the logcat:
FATAL EXCEPTION: main
Process: com.master.tobias.phono, PID: 10721
android.database.CursorIndexOutOfBoundsException: Index -1 requested, with a size of 1
Edit: The query works fine with the DB Browser for SQLite.
Try cursor.moveToFirst() before accessing the cursor data
try this one
public Cursor getData(int id){
SQLiteDatabase db = this.getWritableDatabase();
String query = "SELECT * FROM " + TABLE_NAME + " WHERE ID = " + id;
Log.d(TAG, query);
Cursor cursor= db.rawQuery(query, null);
while(cursor.moveToFirst()){
//get your value over here
}
return data;
}
It's also beneficial to look at the Android documentation of methods as it provides more information as to what the method if expecting as parameters and will be returning. Firstly, the db.rawQuery
Runs the provided SQL and returns a Cursor over the result set.
SQLiteDatabase
As for the cursor, you need to check the existence of an object with the Cursor variable. This can be done via using the following method:
cursor.moveToFirst();
Move the cursor to the next row.
This method will return false if the cursor is already past the last entry in the result set.
Cursor
This method will return a boolean which you can use for further validation. If the boolean is false, the cursor doesn't contain any data/objects within. If it's true, you know you have existence of the data.
Therefore, you are missing this functionality where you'll need to move the object to the first row which will allow you to determine if the query was empty or not.
This is my code :
Db.getInstance().beginTransaction();
int i = Db.getInstance().delete("friends", null, null);
Log.e(TAG, "dropDB: " + i);
Db.getInstance().setTransactionSuccessful();
Db.getInstance().endTransaction();
I have searched the SO community, but cannot find what is wrong in this code. When I delete , the value of i is number of rows deleted, but still the database keeps returning rows.
Db is my own helper class in which I initialise the SQLiteDatabase's object and get getWritableDatabase().
May be nothing, but try only calling getInstance() once and setting it to a variable.
I use this in a CustomDialog when the user clicks the btnYES to delete the table.
I know the table only ever has one record because it hold a password so try this
db = helper.getReadableDatabase();
String q = "SELECT * FROM masterPW";
Cursor cursor = db.rawQuery(q,null);
// Above query gets TABLE_PW data from Col_IDI
// TABLE_PW will only ever have one row of data
int rowID = 99;
if(cursor.moveToFirst()){
rowID = cursor.getInt(cursor.getColumnIndex(Col_IDI));
str = cursor.getString(cursor.getColumnIndex(Col_MPW));
}
cursor.close();
// Line of code below WORKS deletes entire TABLE <=====
// Not a recommended way to re-set the master password
// db.delete(TABLE_PW, null, null);
I am trying to get the last 3 entries made to the database. Im using the following code but im only getting the last entry not the last 3.
String query = "Select * from " + TABLE_DETAILS + " DESC limit 3;";
SQLiteDatabase db = this.getWritableDatabase();
Cursor cursor = db.rawQuery(query, null);
if (cursor.moveToFirst()) {
cursor.moveToFirst();
System.out.println(Integer.parseInt(cursor.getString(2)));
cursor.close();
} else {
}
db.close();
Thanks
You'll need to loop with the cursor to get all result rows, e.g. instead of
if (cursor.moveToFirst()) {
...
loop like this
while (cursor.moveToNext()) {
System.out.println(cursor.getString(2));
}
cursor.close();
To change the ordering, add ORDER BY <expression> to your query, for example
SELECT ... ORDER BY _id DESC LIMIT 3
I am just trying to search for the data in multiple table.If the where condition data is not present in first table(tab1) then it has to search in the second table(tab2) but I am getting the exception showing that
Cursor Index Out of Bounds Exception: Index -1 requested with size 0
Here is my code
SQLiteDatabase db=openOrCreateDatabase("train",SQLiteDatabase.CREATE_IF_NECESSARY, null);
Cursor c1;
String[] table={"tab1","tab2","tab3","tab4"};
int i=0;
do {
c1 = db.rawQuery("select * from '"+table[i]+"' where name='Triplicane'", null);
i++;
} while(c1 == null);
int id1=c1.getInt(0);
String nam1=c1.getString(1);
Toast.makeText(fare.this,"ID no:"+id1, Toast.LENGTH_LONG).show();
Toast.makeText(fare.this,"name"+nam1, Toast.LENGTH_LONG).show();
So from the beginning. Implicitly, each Cursor is positioned before first row so if you want to work with it you need to call
cursor.moveToFirst()
that moves Cursor to first row if is not empty and then is ready for work. If Cursor is empty simply it returns false. So how i mentioned now this method is very handy indicator whether your Cursor is valid or not.
And as my recommendation i suggest you to change your code because i think is broken and it sounds like "spaghetti code"
Cursor c = null;
String[] tables = {"tab1", "tab2", "tab3", "tab4"};
for (String table: tables) {
String query = "select * from '" + table + "' where name = 'Triplicane'";
c = db.rawQuery(query, null);
if (c != null) {
if (c.moveToFirst()) { // if Cursor is not empty
int id = c.getInt(0);
String name = c.getString(1);
Toast.makeText(fare.this, "ID: " + id, Toast.LENGTH_LONG).show();
Toast.makeText(fare.this, "Name: " + name, Toast.LENGTH_LONG).show();
}
else {
// Cursor is empty
}
}
else {
// Cursor is null
}
}
Notes:
Now i want to tell you some suggestions:
An usage of parametrized statements is very good practise so in a
future if you will work with statements, use placeholders in them. Then your statements becomes more human-readable, safer(SQL Injection) and faster.
It's also a very good practise to create static final fields that will hold
your column names, table names etc. and to use
getColumnIndex(<columnName>) method to avoid "typo errors" which are looking for very bad.
Your Cursor flag to empty row , On Sqlite cursor pointed to row number -1 ,
then if you use c.moveNext() or c.moveToFirst() you'll be able to read rows "row by row "
write cursor.movetoFirst() before getting data from cursor.
I am using SQLite in Android.
I have the query, query executed and how to print count from cursor.
Cursor dataCount = mDb.rawQuery("select count(*) from " + DATABASE_JOURNAL_TABLE, null);
I have no record in table.
You already have the correct approach.
Cursor cursor = database.rawQuery("select count(*) from " + DATABASE_JOURNAL_TABLE, null);
// ensure there is at least one row and one column
if (cursor.getCount() > 0 && cursor.getColumnCount() > 0) {
cursor.close();
return cursor.getInt(0);
} else {
cursor.close();
return 0;
}
You must check that there is at least 1 row and 1 column, if you provide a table that does not yet exist there will be no column to access and cursor.getInt(0) will throw an exception.
source: https://github.com/samkirton/SQLKing
May be by getInt(index) as
cursor.getInt(1); // this is for example, you have to adjust index in your code
Also cursor has a built in function getCount() to return row number so can also do like this:
// assuming your table has `id` column as primary key or unique key.
Cursor dataCount = mDb.rawQuery("select id from " + DATABASE_JOURNAL_TABLE, null);
dataCount.getCount();
See android devloper's doc for Cursor for more information.