I'm using SQLite DB in my Android app.
Now I need to implement data extraction in the same order in which it was inserted.
Is it enough to do SELECT ... ORDER BY _id ... if the _id column is INTEGER PRIMARY KEY AUTOINCREMENT?
Or should I add a column to store the date and time a row has been created?
You can use ORDER BY _id. Make sure you are using a List and not a Set....
No need, an id generated by AUTOINCREMENT is enough.
Yes, if you just need the order, you may use such statement or just simple "SELECT ... FROM sometable". Results will be equals.
Related
I am using this query
"select * from SomeTable group by SomeColumn"
It is returns list with accenting order, but i need to same order like in database.
For example the order in database is:
p
a
s
But result is:
a
i
p
Sample
The result need to be like distinct by CityEN but with all columns and order like 1.Paris 2.Amsterdam 3.Istanbul
In Sqlite, each row of a table has a unique rowid, which you can use for sorting.
select * from SomeTable group by SomeColumn order by rowid;
In your statement, add this line to sort the results:
order by min(rowid)
Your query does not enforce any order with ORDER BY clause so no assumption about row order should be made. If you want specific order add i.e. ORDER BY SomeColumn. See docs about all available order options: https://www.sqlite.org/lang_select.html#orderby
By the rules of SQL, you can't count on getting records back in any specific order without specifying an ORDER BY clause in your SQL query.
In practice servers sometimes return values in the order in which they're inserted, in the order of the first index created, or in the order of the primary key--but you can't count on this behavior, and in fact I've seen the behavior change between database maintenance windows or after the database version is upgraded. You definitely wouldn't want to count on a DB engine to give you back records in any particular order if you write a SELECT statement without an ORDER BY clause.
The only real way to get your records back in the order you inserted them is to create a timestamp column and then sort on it during the SELECT. If you don't want to worry about populating that column on INSERT, have that column auto-populate itself with a timestamp (depending on your DB engine).
I have some kind of this table.
The question is what is the best way to create this kind of table?
Should I create for each item one table is it possible to create only one table??
Updated: See comments under #Emil.
You should have 1 tables as #Emil has suggested.
This should look like, soemthing like
_id, sort, grade, diameter, length, price1_dol, price1_euros, price2_dol, price2_euros, final,
Note: I have split up prices columns up - so you have price1_dol, price1_euros, price2_dol, price2_euros.
It is indeed possible to make this data into just one table. The columns sort and grade seem to uniquely identify one row so together they might make up a candidate key. If so you could use those as your primary key, or create a new integer column that you use as the primary key.
You should definitely not create one table per item. The database schema should never change with normal use. Only when you add, remove or change the type of data you have in your database should you consider changing the schema. Otherwise you should design and normalize your database in such a way that it's possible to grow the data only by inserting new rows, not new tables.
This is the query that I use to create a table
create table site_table(
_id integer primary key autoincrement,
name_site text,
url text,
login text,
pass text
);
I called Cursor.getColumnNames() and noticed that columns order are id, login, pass, name, url.
So, if I want a value I have to get it by the index Cursor.getString(index). Until I debugged I was messing up calling the wrong index, but now I wonder, why SQLite saves that way? Why it does not follow that way I created id, name_site, url, login and pass?
Thanks
So, if I want a value I have to get it by the index
Cursor.getString(index)
So for example for this reason you should always use
c.getString(c.getColumnIndex("ColName")); // or better getColumnIndex(CONSTANT)
This method saves all of us and ensure that you never get wrong results. Generally this method is recommended and also storing COLUMN_NAMES as CONSTANTS in separated class is very, very useful and efficient practise.
Note: Order depends on projection i.e. select name, lastname from table
That data is ordered by the order your requested it in your query, not the order you created the table with. So you probably changed the order in your query that generated said cursor.
Columns order in your cursor depends on projection. To be sure you use correct column index use c.getString(c.getColumnIndexOrThrow("COLUMN_NAME")) where c is your cursor.
I just made the experience first hand:
The indices of the columns of the cursor as a result of a
SELECT * FROM mytable WHERE ...
query have sometimes (not always) a different order that what SQLITE Database Browser shows as column order in the Database Structure tab. So referencing the columns via getColumnIndex seems to be the only safe way.
I am having a table with 'int' column. During software upgrade, I want to change it to 'long' data type. It seems SQLite does not provide an option (in alter statement) to change/modify column properties. Since I want to do an upgrade, the table might contain data which the user should not lose. So please suggest me a good method to change the column data type property without data loss.
One way suggested in the search links is to create a temporary table, copy the records from the existing table, delete the existing table, and rename the temporary table. I doubt that is efficient.
Your help appreciated!
Regards
Vivek Ragunathan
I used the follow statements to change the type of the column.
CREATE TABLE IF NOT EXISTS **TEMP_TABLE** (id integer primary key autoincrement, **col2change integer not null**, ...)
INSERT INTO TEMP_TABLE SELECT * FROM EXISTING_TABLE
DROP TABLE EXISTING_TABLE
ALTER TABLE TEMP_TABLE RENAME TO EXISTING_TABLE
I changed the int type column in the existing table to integer type. For a few hundred rows, it was reasonably fast.
SQLite3 columns do not have data types, only affinities -- there is no benefit in changing the column type from int to long.
If a wrapper program is truncating values before giving them to SQLite3, there is a way to fix this by editing the schema. It is a dangerous operation, so do it only after backing up your database. The schema is stored in the table sqlite_master; normally it is read-only, but you can modify it if you enable it with the writable_schema pragma. Be careful to only make changes that do not invalidate your data; you may change int to long int since they both have INTEGER affinity.
From SQLite documentation
It is not possible to rename a column, remove a column, or add or
remove constraints from a table.
Check this link
Please do remember that column data types are not rigid in SQLite. Check this link
Edit:
Following your comments on another answer, I guess the option you mentioned - working through the temp table - is the only one, which is not efficient off course.
you could add a new colum, copy the values form the old to the new column, delete the old column and then rename the new column to the old name
AFAIK there is no way in Android to change column data types once a table is created and used. The practiced way is to make a new table and copy the data which you read about
Really all I want to do is say the query SELECT DISTINCT column FROM table but I can't figure out how to structure it in the enourmous query methods that are part of SQLiteDatabase
I'm just trying to get the names of all contacts in a table.
You seem to know the sql query you want to run. Have you tried using rawQuery()?
You will probably find this version of the SQLiteDatabase#query method most useful.