I have a database that represent music shop data.
Tables I want to work with are (artist, album, track)
every album has an albumID, title and artistID
and every track has TrackID, Milliseconds, albumID and name
well, as you know every album has many tracks
I want to calculate the sum of all songs in the album(in Milliseconds) Then get the average of that sum to get the albums that are above the average in length.
I managed to calculate the length of every album but i struggled to get the average.
I want to generate a table that will be like that.
---------------------------------------------------------------------
AlbumID | Tile | Milliseconds
---------------------------------------------------------------------
1- | |
2- | |
3- | |
...
10- | |
----------------------------------------------------------------------
Sample table of Track
TrackID | Name | AlbumId | Milliseconds
1 For Those About To Rock 1 343719
6 Put The Finger On You 1 205662
7 Let's Get It Up 1 233926
85 Cochise 10 222380
86 Show Me How to Live 10 277890
87 Gasoline 10 279457
88 What You Are 10 249391
89 Like a Stone 10 294034
99 Your Time Has Come 11 255529
100 Out Of Exile 11 291291
101 Be Yourself 11 279484
102 Doesn't Remind Me 11 255869
111 Money 12 147591
112 Long Tall Sally 12 106396
so, LIMIT 10
and the length of the track
I believe that the following may be what you wish :-
WITH albumsums(id,asum) AS (
SELECT albumid, sum(milliseconds)
FROM track
GROUP BY albumid
)
SELECT album.albumid, album.title, asum
FROM album
JOIN albumsums
ON album.albumid = albumsums.id
WHERE asum > (SELECT avg(asum) FROM albumsums)
LIMIT 10;
Consider the following demo :-
DROP TABLE IF EXISTS track;
DROP TABLE IF EXISTS artist;
DROP TABLE IF EXISTS album;
CREATE TABLE IF NOT EXISTS track (trackid INTEGER PRIMARY KEY, name TEXT, milliseconds INTEGER, albumid);
CREATE TABLE IF NOT EXISTS artist (artistid INTEGER PRIMARY KEY, artistname TEXT);
CREATE TABLE IF NOT EXISTS album (albumid INTEGER PRIMARY KEY, title TEXT, artistid INTEGER);
INSERT INTO artist (artistname) VALUES ('Pink Floyd'),('Genesis'),('Deep Purple');
INSERT INTO album (title,artistid) VALUES('Dark side of the moon',1),('Fireball',3),('Foxtrot',2);
INSERT INTO track (name,milliseconds,albumid) VALUES
('Supper''s Ready',((22 * 60) + 57) * 1000,3),
('Watcher of the Skies',((7 * 60) + 21) + 1000,3),
('Time Table',((4 * 60) + 47) * 1000,3),
('Get ''Em Out by Friday',((8 * 60) + 35) * 1000,3),
('Can-Utility and the Coastliners',((5 * 60) + 45 ) * 1000,3),
('Speak to me /Breath',((3 * 60) + 58) * 1000,1),
('On the Run',((3 * 60) + 35) * 1000,1),
('Time',((7 * 60) + 5) * 1000,1),
('The Great Gig in the Sky',((4 * 60) + 44) * 1000,1),
('Money',((6 * 60) + 23) * 1000,1),
('Use and Them',((7 * 60) + 50) * 1000,1),
('Any Colour you Like',((3 * 60) + 26) * 1000,1),
('Brain Damage',((3 * 60) + 47) * 1000,1),
('Fireball',((3 * 60) + 24) * 1000,2),
('No No No',((6 * 60) + 54) * 1000,2),
('Demon''s Eye',((5 * 60) + 21) * 1000,2),
('Anyone''s Daughter',((4 * 60) + 43) * 1000,2),
('The Mule',((5 * 60) + 21) * 1000,2),
('Fools',((8 * 60) + 19) * 1000,2),
('No One Came',((6 * 60) + 34) * 1000,1),
('Strange Kind of Woman',((4 * 60) + 07) * 1000,1)
;
SELECT * FROM artist;
SELECT * FROM album;
SELECT * FROM track;
SELECT albumid, sum(milliseconds)
FROM track
GROUP BY albumid
;
WITH albumsums(id,asum) AS (
SELECT albumid, sum(milliseconds)
FROM track
GROUP BY albumid
)
SELECT album.albumid, album.title, asum, (SELECT avg(asum) FROM albumsums AS album_average_for_demo)
FROM album
JOIN albumsums
ON album.albumid = albumsums.id
WHERE asum > (SELECT avg(asum) FROM albumsums);
The net result (as you wanted above average) being just one album above the average :-
The CTE (Common Table Expression albumsums) as demonstrated by the previous query produces 3 rows (1 per album) with the album id and the sum of the tracks :-
Thus the average album length is 2552147 and thus only 1 album is greater than that (as would be expected from such a limited amount of data).
The tables (after being loaded) being :-
I want to execute cron every day on midnight at time 00:01 Hrs.
Is the following cron time correct?
1 0 * * * *
Yes the cron time is correct.
1 0 * * * /mydir/myscript
should be your cron entry.
Each cron entry consists of six fields, in the following order:
minute(s) hour(s) day(s) month(s) weekday(s) command(s)
0-59 0-23 1-31 1-12 0-6
1 0 * * * /mydir/myscript <-- Correct 1 minute after midnight
1 0 * * * * <--- Incorrect, Syntax Error
0 1 0 * * ?
or
1 0 * * *
You can generate crons example with https://www.freeformatter.com/cron-expression-generator-quartz.html
Let's get the definitions straight: cron is a daemon that is designed to run continuously and execute commands at specified intervals when you tell it to.
To do that, it needs two things: an interval and a command.
Your example has a valid interval, but is missing a command to execute one minute after midnight:
1 0 * * * * /path/to/executable/or/script/here
I need to get he difference between end date and start date in milliseconds inside a view in oracle 11g. I can get these two dates from the database in 07-JUN-12 04.32.21.092000000 AM format. All I need is to find the diff of these kind of dates in milliseconds
SELECT ((extract(DAY FROM time2-time1)*24*60*60)+
(extract(HOUR FROM time2-time1)*60*60)+
(extract(MINUTE FROM time2-time1)*60)+
extract(SECOND FROM time2-time1)) *1000
as millisecs FROM dual;
can be done using above approach
select (DATE1 - DATE2) as days,
(DATE1 - DATE2) * 24 as hours,
(DATE1 - DATE2) * 24 * 60 as minutes,
(DATE1 - DATE2) * 24 * 60 * 60 as seconds,
(DATE1 - DATE2) * 24 * 60 * 60 * 1000 as milliseconds
from dual
EDIT - I assumed DateTime type. However, Justin Cave's question is very relevant. A Timestamp is not the same as a DateTime, so my answer won't work if you are dealing with Timestamps.
In that case, see this http://www.dba-oracle.com/t_timestamp_math_elapsed_times.htm.
How can I convert an int value (ie: 1800) which represents minutes into a value that looks like this: dd:hh:mm (days:hours:minutes).
So 1800 should be converted into 1:06:00 (1 day 6 hours 0 minutes).
In a stored procedure I have this:
SELECT
Record_ID, Project_ID, Ticket_ID, WO_Type, DC, Title, Device_Quantity,
Total/1440 as Total,
((Total - Elapsed) - DATEDIFF(mi, Record_Time, getdate())) as FinalTimeLeft,
Completed
FROM Record
How would I implement the casting into the SP? Above FinalTimeLeft=1800
How about this example - it does hours, minutes and seconds but it should be easy to modify for days, hours and minutes:
SELECT
CAST(mins / 3600 AS VARCHAR) + ':' +
RIGHT('0' + CAST((mins % 3600) / 60 AS VARCHAR), 2) + ':' +
RIGHT('0' + CAST(mins % 60 AS VARCHAR), 2)
FROM
(SELECT 1800 AS mins) a
EDIT: Included your stored procedure with my code amended for day, hour and minute:
SELECT
*
,CAST(FinalTimeLeft / 1440 AS VARCHAR) + ':' +
RIGHT('0' + CAST((FinalTimeLeft / 60) % 24 AS VARCHAR), 2) + ':' +
RIGHT('0' + CAST(FinalTimeLeft % 60 AS VARCHAR), 2) AS duration
FROM (
SELECT
Record_ID
,Project_ID
,Ticket_ID
,WO_Type
,DC
,Title
,Device_Quantity
,Total/1440 as Total
,((Total-Elapsed)-DATEDIFF(mi,Record_Time,getdate())) as FinalTimeLeft
,Completed
FROM record) a
I am trying to express the difference of two given dates in days, hours, and minutes (like 1 day, 6 hours, 17 minutes.) as SQLite query output. I have entryin and entryout as datetime fields in a SQLitedatabase. I tried all combinations of julianday and strftime but still running into rough weather.
I tried strftime('%d %H:%M', julianday(entryout)-julianday(entryin)). For a row the values are 2011-11-10 11:46, and 2011-11-09 09:00. but the output is 25 14:46 instead of 01 02:46.
Can some one help me with this, or point me correct logic for this? Thanks in advance.
You can try something like this:
SELECT
CAST((strftime('%s', '2011-11-10 11:46') - strftime('%s', '2011-11-09 09:00')) / (60 * 60 * 24) AS TEXT) || ' ' ||
CAST(((strftime('%s', '2011-11-10 11:46') - strftime('%s', '2011-11-09 09:00')) % (60 * 60 * 24)) / (60 * 60) AS TEXT) || ':' ||
CAST((((strftime('%s', '2011-11-10 11:46') - strftime('%s', '2011-11-09 09:00')) % (60 * 60 * 24)) % (60 * 60)) / 60 AS TEXT);