PHP / MYSQL:慢慢迭代6k行,每行创建新记录 - 算法

时间:2013-05-23 05:30:02

标签: php mysql algorithm select recursion

我很抱歉这个愚蠢的问题,但我有一天,我觉得自己是最愚蠢的程序员。我需要你的帮助。我目前正在使用PHP和MYSQL开发,我喜欢超低技能,我正在从事继承项目。

我有几乎6k记录的数据库表,比方说TABLE_A,我需要遍历表A中的记录,并且每个记录在表B中创建两个新记录,其中来自TABLE_A(Id)的PK是FK在TABLE_B中。没什么特别的吗?所以我还有一件事,这件事正在发生,请不要责怪,在生产DB中。所以我得到了一个请求,只需每1秒钟就有10条记录进入表B。此外,我有一个看起来像这样的ID列表:1,2,4,6,7,8,9,11,12,15,16,...到6k。所以我基本上不能这样做:

for ($i = 1; $i <= MAX(id); $i++) {
    //create two new records in TABLE B
}

我花了一些时间进行研究,我需要与你们讨论这个问题,想出一些想法。 我不想要您的确切解决方案,但我想学习如何思考以及如何提出解决方案。我在回家的路上想着它。所以我只是在脑海中创建了算法。以下是关于我所知道的以及我可能会使用的内容的逐步过程:

  1. 我知道我每1秒只能运行10次插入 - 所以我需要在一个批次中限制表A中的选择仅5行。
  2. 所以我可以使用MySQL语法:LIMITOFFSET,例如:select * from t LIMIT 5 OFFSET 0
  3. 这意味着我必须存储上一批中最后一条记录的ID。
  4. 完成当前批处理后,我需要在开始新批处理之前等待1秒钟(我考虑使用PHP方法sleep())。
  5. 我需要循环
  6. TABLE_A中的确切行数现在不可用
  7. 插入新记录很简单。专注于迭代。
  8. 所以这是我在纸上的东西,我不太确定它是否会起作用,因为我真的想从这个问题中学到一些东西。我将跳过周围的事情,比如连接数据库等,并将只关注算法,并将编写一些混合的PHP / Mysql / Pseudo代码。

    $limit=5
    $offset=0;
    
    function insert($limit, $offset){
       $stm = $db->prepare("SELECT id FROM tableA LIMIT :limit OFFSET :offset");
       $stm->execute(array('limit' => $limit, 'offset' => $offset));
       while($stm->rowCount() > 0){ 
          $data = $stm->fatchAll();
          foreach($data as $row){
             // insert into TABLE_B
          }
          sleep(1);
          $offset +=5;
          $this->insert($limit, $offset);
       }
    }
    

    我不完全确定,如果这种递归会起作用。在纸面上它看起来很可行。但性能呢?在这种情况下这是一个问题吗?

    也许主要的问题是:我是不是在想这个?你知道如何更好地解决这个问题吗?

    感谢您提供有关如何提出可行解决方案的任何评论,想法,建议,想法和详细说明。可能我应该深入研究一些算法分析和设计。你知道什么好资源吗?

    (抱歉语法错误,我不是母语人士)

1 个答案:

答案 0 :(得分:3)

我不知道为什么你必须每1秒插入表B 10条记录,但我们假设这条件不能改变。

您的源代码是正确的,但是这里不需要递归,我们应该做类似的事情。

limit=5
offset=0

while (itemsA = fetch_from_a(limit, offset)) {
    # you should do a batch insertion here, see MySQL's documentation.
    insert_into_B(itemsA);         
    sleep(1);
    offset += 5;
}

# prototype
# fetch some records from table A, return array of found items 
# or an empty array if nothing was found.
function fetch_from_a(limit, offset);