MySQL Querying database for time periods not already assigned

I have a rather complex-seeming query that will form the basis for an online classroom scheduling tool. My challenge is to develop a method to identify which classes a user is signed up for in the st_schedule table, then deduce from the overall table of classes, st_classes, which other classes are available that don't conflict with the user's current classes.

For example, if a user has an entry in st_schedule assigning them to a class from 8:00am to 9:00am, they would be ineligible for any class whose time fell between 8:00am and 9:00am. A class that ran 7:15am - 8:15am would make the user ineligible. I store the start times and end times of classes in the database separately for comparison purposes. It's important that this be as flexible as possible, so the concept of "blocking" times and assigning times to blocks is not a possibility.

Here are excerpts from the tables:

table st_classes (holds class information)
id
start_time
end_time

table st_schedule (holds schedule information)
id
user_id
class_id

I certainly could do this in a series of loops server-side, but I have to think that there's a MySQL method that can do this type of operation in one fell swoop.

This question and answers originated from www.stackoverflow.com
Question by (4/13/2011 3:11:18 AM)

Answer

This is using table variables in mssql but the sql selects should translate over to mysql

First the sample data

DECLARE @st_classes TABLE
    (
     ID INT NOT NULL,
     Title VARCHAR(40) NOT NULL,
     StartTime DATETIME NOT NULL,
     EndTime DATETIME NOT NULL
    )       

DECLARE @st_schedule TABLE
    (
     ID INT NOT NULL,
     UserID INT NOT NULL,
     ClassID INT NOT NULL
    )       

INSERT INTO @st_classes (ID, Title, StartTime, EndTime)
SELECT 1,'Class1','08:00:00','09:30:00' UNION 
SELECT 2,'Class2','09:30:00','11:30:00' UNION
SELECT 3,'Class3','11:30:00','16:00:00' UNION
SELECT 4,'Class4','16:00:00','17:30:00' UNION
SELECT 5,'Class5','09:00:00','11:45:00' UNION
SELECT 6,'Class6','07:00:00','18:00:00' 

INSERT INTO @st_schedule(ID, UserID, ClassID)
SELECT 1,1,1 UNION
SELECT 2,1,2 UNION
SELECT 3,2,6

Next a bit of sql to confirm the tables join OK (selecting scheduled courses for user with an ID of 1) - Returns class 1 and 2

SELECT *
FROM    @st_schedule AS S INNER JOIN 
        @st_classes AS C ON S.ClassID = C.ID
WHERE  S.UserID = 1 

Now we need to select all the ID of the courses where they overlap time wise with the users scheduled ones (including the scheduled ones) - Returns 1,2,5,6

SELECT  AC.ID
FROM    @st_classes AS AC
        INNER JOIN ( SELECT C.StartTime,
                            C.EndTime
                     FROM   @st_schedule AS S
                            INNER JOIN @st_classes AS C ON S.ClassID = C.ID
                     WHERE  S.UserID = 1
                   ) AS UC ON ( AC.StartTime < DATEADD(ss, -1, UC.EndTime)
                                AND DATEADD(ss, -1, UC.EndTime) > UC.StartTime
                              )
GROUP BY AC.ID 

Now we need to select all courses where the Course ID is not in our list of overlapping course IDs. - Returns course 3 and 4

SELECT  *
FROM    @st_classes
WHERE   ID NOT IN (
        SELECT  AC.ID
        FROM    @st_classes AS AC
                INNER JOIN ( SELECT C.StartTime,
                                    C.EndTime
                             FROM   @st_schedule AS S
                                    INNER JOIN @st_classes AS C ON S.ClassID = C.ID
                             WHERE  S.UserID = 1
                           ) AS UC ON ( AC.StartTime < DATEADD(ss, -1, UC.EndTime)
                                        AND DATEADD(ss, -1, UC.EndTime) > UC.StartTime
                                      )
        GROUP BY AC.ID )

Change the user ID filter to 2 and you should not get any returned as the course assigned to that user overlaps all courses.

Answer by

Find More Answers
Related Topics  mysql  query  time
Related Questions
  • Best way to query mysql for total time worked in a day

    I'm trying to come up with the best way to add the total time an employee was clocked in. The punch types are day in, break out, break in & day out . You would think I could just select * whe…
  • mySQL query for selecting time periods

    I have a timestamp field and I want to select * where time [is within the last 24 hours] What is the correct query for this?
  • Mysql Average on time column?

    SELECT avg( duration ) as average FROM `login`; The datatype for duration is "time", thus my value is like: 00:00:14, 00:20:23 etc I execute the query it gives me: 2725.78947368421 What is…
  • How can I COUNT the number of rows in a database for different time periods?

    I've got a table in a Sybase DB with a column createdDateTime. What I want to be able to do is count how many rows were created between specific but accumulating time periods, ie: 7:00 - 7:15 7:00…
  • Group MySQL Data into Arbitrarily Sized Time Buckets

    How do I count the number of records in a MySQL table based on a timestamp column per unit of time where the unit of time is arbitrary? Specifically, I want to count how many record's timestamps …
  • How do I difference time in MySQL query?

    There's a datetime field "time" and it's in Y-m-d H:i:s format. All the values are past values. I need to query that field diffed from current time resulting in seconds. SELECT time FROM table
  • MySql query execution time

    I am using MySQL Workbench on Windows. How do I find out the time taken to execute a query like Select * from employers where employerid > 200 Is there a statement I can enter that returns…
  • combining 2 time series

    I am working with price data for futures contracts. I have data for Dec. 2010 and Mar. 2011, that I have loaded into the db. I want to generate a flat file with the time series that includes both co…
  • MYSQL PHP querying already queried data ( Filtering already filtered data)

    I have a complex query that returns more than 30,000 records . We are showing user at a time 100 records and user has to click on next to get next 100 records . Here the problem is we are running…
  • Query time result in MySQL w/ PHP

    Is there a way that I can get the time of a MySQL query (specifically with PHP)? The actual time it took to complete the query, that is. Something such as: Results 1 - 10 for brown. (0.11 seconds…