idea was to have a new table for each date
Individual tables could be complicated, say there is a need for a month's worth of data, what would be done? Each table will take up a minimum of 4k and could perhaps result in 2k unused disk space per table.
Another idea was to have each row a new ticker with the relevant info
as before in the columns but include the date as well.
This is closer BUT what is relevant data. I not at all clued up on tickers, stocks etc. But if other relevant data is repeated e.g. say ACME being the code for the stock, then repeating that data time and time again can be a waste of space and inefficient.
Here's an example, intended as a pointer rather than a solution to use, that explains using tables with relationships that can reduce duplicated data (normalise the data to some extent).
For this simple example you'd likely have a table for the stock and it's static/rarely changed but often used(referred to) data (such as the company name).
You'd then likely have a table for the activity (that would include the date) that references (has a relation ship with) the more static data.
- Say ACME changed it's code, with your idea you'd have to change the
name in every row where ACME was recorded (not hard but inefficient)
in comparison to the single change needed if 2 related tables were used.
The following is an example of SQL that creates, populates and queries (extracts) the tables as discussed.
/* Deletes the 2 tables just in case they exist and allows the example to be rerun */
DROP TABLE IF EXISTS stock;
DROP TABLE IF EXISTS activity;
/* Create the stock table with 3 columns
1st is a unique identifier that will be used for reference the stock
2nd is for the stock code
3rd is for the company name
*/
CREATE TABLE IF NOT EXISTS stock (
id INTEGER PRIMARY KEY,
code TEXT,
company TEXT
)
;
/*
Create the activity table with 4 columns
id not really needed BUT exists anyway (search for rowid to find out more)
the date and time the activity occured with a default value that will be the current timestamp (special)
the id value of the id column in the stock row to which the activity relates (the relationship)
the amount (change) made
*/
CREATE TABLE IF NOT EXISTS activity (
id INTEGER PRIMARY KEY,
activity_date INTEGER DEFAULT CURRENT_TIMESTAMP,
related_stock INTEGER,
activity_amount INTEGER
)
;
/*
Add 3 stock rows
*/
INSERT INTO stock (id,code,company)
VALUES
(1,'ACME','ACME COMPANY')
,(2,'IBM','International Business Machines')
,(100,'MSFT','Microsoft')
;
/*
add some activity for the stocks (see results)
*/
INSERT INTO activity
(related_stock,activity_amount)
VALUES
(1,+100),(1,-10),(1,+8)
,(2,75),(100,60),(1,-5),(2,+10),(100,-4),(100,+16)
;
/* Get the results of the activities */
SELECT
stock.code,
stock.company,
sum(activity.activity_amount) AS end_amount, /* user the aggregate function to sum the amounts in the group */
group_concat(activity.activity_amount,' ') AS activities /* use the aggregate function to get all the values separated by a space */
FROM stock /* parent table */
JOIN activity ON activity.related_stock = stock.id /* related table and how to relate it */
GROUP BY /* make groups according to :- */
stock.id
;
When the above is run (in a third party SQLite tool (NaviCat SQLite used))
The Query (SELECT .... ) produces :-
