MySQL query does not return any data - database

I need to retrieve data from a specific time period.
The query works fine until I specify the time period. Is there something wrong with the way I specify time period? I know there are many entries within that time-frame.
This query returns empty:
SELECT stop_times.stop_id, STR_TO_DATE(stop_times.arrival_time, '%H:%i:%s') as stopTime, routes.route_short_name, routes.route_long_name, trips.trip_headsign FROM trips
JOIN stop_times ON trips.trip_id = stop_times.trip_id
JOIN routes ON routes.route_id = trips.route_id
WHERE stop_times.stop_id = 5508
HAVING stopTime BETWEEN DATE_SUB(stopTime,INTERVAL 1 MINUTE) AND DATE_ADD(stopTime,INTERVAL 20 MINUTE);
Here is it's EXPLAIN:
+----+-------------+------------+--------+------------------+---------+---------+-------------------------------+------+-------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+------------+--------+------------------+---------+---------+-------------------------------+------+-------------+
| 1 | SIMPLE | stop_times | ref | trip_id,stop_id | stop_id | 5 | const | 605 | Using where |
| 1 | SIMPLE | trips | eq_ref | PRIMARY,route_id | PRIMARY | 4 | wmata_gtfs.stop_times.trip_id | 1 | |
| 1 | SIMPLE | routes | eq_ref | PRIMARY | PRIMARY | 4 | wmata_gtfs.trips.route_id | 1 | |
+----+-------------+------------+--------+------------------+---------+---------+-------------------------------+------+-------------+
3 rows in set (0.00 sec)
The query works if I remove the HAVING clause (don't specify time range). Returns:
+---------+----------+------------------+-----------------+---------------+
| stop_id | stopTime | route_short_name | route_long_name | trip_headsign |
+---------+----------+------------------+-----------------+---------------+
| 5508 | 06:31:00 | "80" | "" | "FORT TOTTEN" |
| 5508 | 06:57:00 | "80" | "" | "FORT TOTTEN" |
| 5508 | 07:23:00 | "80" | "" | "FORT TOTTEN" |
| 5508 | 07:49:00 | "80" | "" | "FORT TOTTEN" |
| 5508 | 08:15:00 | "80" | "" | "FORT TOTTEN" |
| 5508 | 08:41:00 | "80" | "" | "FORT TOTTEN" |
| 5508 | 09:08:00 | "80" | "" | "FORT TOTTEN" |
I am using Google Transit format Data loaded into MySQL.
The query is supposed to provide stop times and bus routes for a given bus stop.
For a bus stop, I am trying to get:
Route Name
Bus Name
Bus Direction (headsign)
Stop time
The results should be limited only to buses times from 1 min ago to 20 min from now.
Please let me know if you could help.
UPDATE
The problem was that I was comparing DATE to DATETIME as one answer said.
I could not use DATE because my values had times but not dates.
So my solution was to use Unix time:
SELECT stop_times.stop_id, stop_times.trip_id, UNIX_TIMESTAMP(CONCAT(DATE_FORMAT(NOW(),'%Y-%m-%d '), stop_times.arrival_time)) as stopTime, routes.route_short_name, routes.route_long_name, trips.trip_headsign FROM trips
JOIN stop_times ON trips.trip_id = stop_times.trip_id
JOIN routes ON routes.route_id = trips.route_id
WHERE stop_times.stop_id = 5508
HAVING stopTime > (UNIX_TIMESTAMP(NOW()) - 60) AND stopTime < (UNIX_TIMESTAMP(NOW()) + (60*20));

Stoptime is a time value, and DATE_ADD/SUB work with datetime fields. Ensure they are both the same type.

Try this instead:
SELECT * FROM
(SELECT stop_times.stop_id, STR_TO_DATE(stop_times.arrival_time, '%H:%i:%s') as stopTime, routes.route_short_name, routes.route_long_name, trips.trip_headsign FROM trips
JOIN stop_times ON trips.trip_id = stop_times.trip_id
JOIN routes ON routes.route_id = trips.route_id
WHERE stop_times.stop_id = 5508) AS qu_1
WHERE qu_1.stopTime BETWEEN DATE_SUB(qu_1.stopTime,INTERVAL 1 MINUTE) AND DATE_ADD(qu_1.stopTime,INTERVAL 20 MINUTE);
Have to warn you I haven't tested this but it does remove the need for the HAVING clause.

Don't work with the synthetic column stopTime other than as the output.
I think your query should be something like:
SELECT stop_times.stop_id, STR_TO_DATE(stop_times.arrival_time, '%H:%i:%s') as stopTime, routes.route_short_name, routes.route_long_name, trips.trip_headsign FROM trips
JOIN stop_times ON trips.trip_id = stop_times.trip_id
JOIN routes ON routes.route_id = trips.route_id
WHERE stop_times.stop_id = 5508
AND arrival_time BETWEEN <something> AND <something else>
The HAVING clause you wrote should always return true, so I'm guessing that's not what you really had in mind.

Related

group first started date and last end date for records with a common field

Here is an excerpt of my table data:
|deviceid | |failcount| started | ended |
| a1078 | | 2 | 2020-12-07 14:51:33 | 2020-12-07 17:30:16|
|a1006 | | 2 | 2020-12-09 15:58:01 | 2020-12-09 23:59:59|
|a1006 | | 2 | 2020-12-10 00:00:00 | 2020-12-10 16:40:02|
|a136 | | 71 | 2020-12-18 10:12:19 | 2020-12-18 23:59:59|
|a136 | | 71 | 2020-12-19 00:00:00 | 2020-12-19 04:27:23|
|a1078 | | 36 | 2020-12-21 10:07:09 | 2020-12-21 14:36:40|
What I am trying to get to is to get the earliest start date and the latest end date for each deviceid, BUT for only the same failcount number. The failcount number is the # of failures for each deviceid, so multiple deviceid's can have the same failcount number (should be very few).
This is what im trying to get to:
|deviceid| |failcount| | started | | ended |
|a1078 | | 2 | | 2020-12-07 14:51:33 | |2020-12-07 17:30:16|
|a1006 | | 2 | |2020-12-09 15:58:01 | |2020-12-10 16:40:02|
|a136 | | 71 | |2020-12-18 10:12:19 | |2020-12-19 04:27:23|
|a1078 | | 36 | | 2020-12-21 10:07:09 | |2020-12-21 14:36:40|
I've tried variations of min/max but can't figure out how to keep different failcounts from same deviceid from being combined - for instance, in the above for deviceid a1078, I don't want the started for failcount 2 and the ended for failcount 36.
What I have so far is this but it is combining different failcounts for the same deviceid:
select deviceid
, min(started) as started
, max(started) as ended
from dayfail
where eventno = '600509'
and Convert(char(6),started, 112) = '202012'
group by deviceid
Thx in advance for any assistance to this sql newbie ;)

Design a table around matrix table.

So I have a database that is for selling products. The orders tables hold's the customer's order info like shipping province and Shipping method:
+--------------------+----+
| order | |
+--------------------+----+
| someOtherInfo | |
| shippingMethodID | fk |
| shippingProvinceID | fk |
| basePrice | |
+--------------------+----+
Basically what's happen now is we have a base price for shipping that's based on the Province and Shipping Method. I need to now add that base price for shipping to my orders table and the fact that base price for shipping is a Matrix table or 2d array where col(shipping Method) + Row(Province) = baseCost is throwing me off on how to implement it. I never had to deal with this so Don't even know what to look up.
Example of what the matrix looks like:
+--------+----+----+----+-----+
| | BC | AB | SK | etc |
+--------+----+----+----+-----+
| ground | 9 | 9 | 9 | |
| Air | 15 | 21 | 21 | |
| etc | | | | |
+--------+----+----+----+-----+

SQL Database Constraint | Multi-table Constraint

I need to make 2 database constraints that connect two different tables at one time.
1. The total score of the four quarters equals the total score of the game the quarters belong to.
2. The total point of all the players equals to the score of the game of that team.
Here is what my tables look like.
quarter table
+------+--------+--------+--------+
| gNum | Period | hScore | aScore |
+------+--------+--------+--------+
| 1 | 1 | 13 | 18 |
| 1 | 2 | 12 | 19 |
| 1 | 3 | 23 | 31 |
| 1 | 4 | 32 | 18 |
| | | Total | Total |
| | | 80 | 86 |
+------+--------+--------+--------+
Game Table
+-----+--------+--------+--------+
| gID | hScore | lScore | tScore |
+-----+--------+--------+--------+
| 1 | 86 | 80 | 166 |
+-----+--------+--------+--------+
Player Table
+-----+------+--------+--------+
| pID | gNum | Period | Points |
+-----+------+--------+--------+
| 1 | 1 | 1 | 20 |
| | | 2 | 20 |
| | | 3 | 20 |
| | | 4 | 20 |
+-----+------+--------+--------+
So Virtually I need to use CHECK I think to make sure that players points = score of their team ie (hScore, aScore) and also make sure that the hScore and aScore = the total score in the Game table.
I was thinking of creating a foreign key variable on one of the tables and setting up constraints on that would this be the best way of going about it?
Thanks

How to Write Conditional Statement in SQL Server

I am having a logic issue in relation to querying an SQL database. I need to exclude 3 different categories and any item that is included in those categories; however, if an item under one of those categories meets the criteria for another category I need to keep said item.
This is an example output I will get after querying the database at its current version:
ExampleDB | item_num | pro_type | area | description
1 | 45KX-76Y | FLCM | Finished | coil8x
2 | 68WO-93H | FLCL | Similar | y45Kx
3 | 05RH-27N | FLDR | Finished | KH72n
4 | 84OH-95W | FLEP | Final | tar5x
5 | 81RS-67F | FLEP | Final | tar7x
6 | 48YU-40Q | FLCM | Final | bile6
7 | 19VB-89S | FLDR | Warranty | exp380
8 | 76CS-01U | FLCL | Gator | low5
9 | 28OC-08Z | FLCM | Redo | coil34Y
item_num and description are in a table together, and pro_type and area are in 2 separate tables--a total of 3 tables to pull data from.
I need to construct a query that will not pull back any item_num where area is equal to: Finished, Final, and Redo; but I also need to pull in any item_num that meets the type criteria: FLCM and FLEP. In the end my query should look like this:
ExampleDB | item_num | pro_type | area | description
1 | 45KX-76Y | FLCM | Finished | coil8x
2 | 68WO-93H | FLCL | Similar | y45Kx
3 | 84OH-95W | FLEP | Final | tar5x
4 | 81RS-67F | FLEP | Final | tar7x
5 | 19VB-89S | FLDR | Warranty | exp380
6 | 76CS-01U | FLCL | Gator | low5
7 | 28OC-08Z | FLCM | Redo | coil34Y
Try this:
select * from table
join...
where area not in('finished', 'final', 'redo') or type in('flcm', 'flep')
Are you looking for something like
SELECT *
FROM Table_1
JOIN Table_ProType ON Table_1.whatnot = Table_ProType.whatnot
JOIN Table_Area ON Table_1.whatnot = Table_Area.whatnot
WHERE Table.area NOT IN ('Finished','Final','Redo') OR ProType.pro_type IN ('FLCM','FLEP')
Giving the names of the three tables and the joining criteria will help me improve the answer.

Hive Query: working with String Array

I have a HIVE Table with following schema like this:
hive>desc books;
gen_id int
author array<string>
rating double
genres array<string>
hive>select * from books;
| gen_id | rating | author |genres
+----------------+-------------+---------------+----------
| 1 | 10 | ["A","B"] | ["X","Y"]
| 2 | 20 | ["C","A"] | ["Z","X"]
| 3 | 30 | ["D"] | ["X"]
Is there a query where I can perform some SELECT operation and that returns individual rows, like this:
| gen_id | rating | SplitData
+-------------+---------------+-------------
| 1 | 10 | "A"
| 1 | 10 | "B"
| 1 | 10 | "X"
| 1 | 10 | "Y"
| 2 | 20 | "C"
| 2 | 20 | "A"
| 2 | 20 | "Z"
| 2 | 20 | "X"
| 3 | 30 | "D"
| 3 | 30 | "X"
Can someone guide me how can get to this result. Thanks in advance for any kind of help.
You need to do Lateral view and explode,i.e.
SELECT
gen_id,
rating,
SplitData
FROM (
SELECT
gen_id,
rating,
array (ex_author,ed_genres) AS ar_SplitData
FROM
books
LATERAL VIEW explode(books.author) exploded_authors AS ex_author
LATERAL VIEW explode(books.genres) exploded_genres AS ed_genres
) tab
LATERAL VIEW explode(tab.ar_SplitData) exploded_SplitData AS SplitData;
I had no chance to test it but it should show you general path. GL!

Resources