简体   繁体   English

SQL-在MySQL中遍历表的每一行?

[英]SQL - Looping through ever row of table in mysql?

So I have 2 tables, communication ,and movement . 所以我有2张桌子, communicationmovement

communication has columns fromID , timestamp that has ID of caller, and time the call was made. communication具有fromID列,具有呼叫者ID的timestamp和呼叫时间。 Then I have another table movement that has ID , timestamp , x , y , that has the ID of a person, their location (x,y) , and the time that they are at that location. 然后,我进行了另一个表movement ,该表movement具有IDtimestampxy ,具有一个人的ID,他们的位置(x,y)以及他们在该位置的时间。

I want to write a query that looks something like this: 我想写一个看起来像这样的查询:

For every single row of communication(R)
    SELECT * FROM movement m
    WHERE m.ID = R.fromID && m.timestamp <= R.timestamp
    ORDER BY timestamp 

Basically, what this is doing is finding the closest movement timestamp for a given communication timestamp . 基本上,这是为给定的communication timestamp找到最接近的movement timestamp communication timestamp After that, eventually, I want to find the location (x,y) of a call, based on the movement data. 之后,最终,我想根据movement数据找到呼叫的位置(x,y)

How would I do this? 我该怎么做? I know there's a set based approach, but I don't want to do it that way. 我知道有一种基于集合的方法,但是我不想那样做。 I looked into cursors , but I get the feeling that the performance is terrible on that... so is there anyway to do this with a loop? 我看着cursors ,但是我感到在那方面的表现很糟糕……所以无论如何都要循环执行此操作? I essentially want to loop through every single row of the communication , and get the result... 我本质上是想遍历communication每一行,并得到结果...

I tried something like this: 我尝试过这样的事情:

DELMITER $$ 
CREATE PROCEDURE findClosestTimestamp() 
BEGIN 
DECLARE commRowCount DEFAULT 0; 
DECLARE i DEFAULT 0; 
DECLARE ctimestamp DEFAULT 0; 
SELECT COUNT(*) FROM communication INTO commRowCount; 

SET i = 0; 
WHILE i < commRowCount DO 
SELECT timestamp INTO ctimestamp FROM communication c 
SELECT * FROM movement m 
WHERE m.vID = c.fromID && m.timestamp <= R.timestamp
END$$ 
DELIMITER ; 

But I know thats completely wrong... Is the only way to do this cursors?? 但是我知道那是完全错误的……是做这种游标的唯一方法吗? I just can't find an example of this anywhere on the internet, and I'm completely new to procedures in SQL. 我只是在Internet上的任何地方都找不到这样的示例,而且我对SQL过程完全陌生。 Any guidance would be greatly appreciated, thank you!! 任何指导将不胜感激,谢谢!!

Let's see if I can point you in the right direction using cursors: 让我们看看我是否可以使用光标将您指向正确的方向:

delimiter $$
create procedure findClosestTimeStamp()
begin
    -- Variables to hold values from the communications table
    declare cFromId int;
    declare cTimeStamp datetime;
    -- Variables related to cursor:
    --    1. 'done' will be used to check if all the rows in the cursor 
    --       have been read
    --    2. 'curComm' will be the cursor: it will fetch each row
    --    3. The 'continue' handler will update the 'done' variable
    declare done int default false;
    declare curComm cursor for
        select fromId, timestamp from communication; -- This is the query used by the cursor.
    declare continue handler for not found -- This handler will be executed if no row is found in the cursor (for example, if all rows have been read).
        set done = true;

    -- Open the cursor: This will put the cursor on the first row of its
    -- rowset.
    open curComm;
    -- Begin the loop (that 'loop_comm' is a label for the loop)
    loop_comm: loop
        -- When you fetch a row from the cursor, the data from the current
        -- row is read into the variables, and the cursor advances to the
        -- next row. If there's no next row, the 'continue handler for not found'
        -- will set the 'done' variable to 'TRUE'
        fetch curComm into cFromId, cTimeStamp;
        -- Exit the loop if you're done
        if done then
            leave loop_comm;
        end if;
        -- Execute your desired query.
        -- As an example, I'm putting a SELECT statement, but it may be
        -- anything.
        select *
        from movement as m
        where m.vID = cFromId and m.timeStamp <= cTimeStamp
        order by timestampdiff(SECOND, cTimeStamp, m.timeStamp)
        limit 1;
    end loop;
    -- Don't forget to close the cursor when you finish
    close curComm;
end $$
delimiter ;

References: 参考文献:

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM