【问题标题】:PDO Insert foreachPDO 插入 foreach
【发布时间】:2018-10-09 11:23:39
【问题描述】:

我正在尝试将一个值数组多次插入一个表中。

我有一个简单的数组,由用户选中一个框生成,这就是添加到数组中的内容,然后我想将每个值插入到表中,我想我可以使用 foreach 循环并迭代 $我,但似乎我不能,我不需要担心安全性或其他任何事情,因为这是由两个人在内部使用的。

这是我所拥有的:

foreach($detailsinvoice as $desc){ 
  $conn3 = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );
  $sql3 = "INSERT INTO 
             xero_invoices (ContactName, Description)
             VALUES (:ContactName, :Description)";  
  $st3 = $conn3->prepare ( $sql3 );
  $st3->bindValue( ":ContactName", $this->ContactName, PDO::PARAM_STR );
  $st3->bindValue( ":Description", $desc, PDO::PARAM_STR );
  $st3->execute();
  $this->InvoiceNumber = $conn3->lastInsertId();
  $conn3 = null;
}

这是我的第一次尝试,但收集到连接只能使用一次然后退出,所以我尝试了一次迭代,但我再次了解到你不能用 PDO 语句做到这一点。

$i = 3;
foreach($detailsinvoice as $desc){ 
  $conn[$i] = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );
  $sql[$i] = "INSERT INTO 
             xero_invoices (ContactName, Description)
             VALUES (:ContactName, :Description)";  
  $st[$i] = $conn[$i]->prepare ( $sql[$i] );
  $st[$i]->bindValue( ":ContactName", $this->ContactName, PDO::PARAM_STR );
  $st[$i]->bindValue( ":Description", $desc, PDO::PARAM_STR );
  $st[$i]->execute();
  $this->InvoiceNumber = $conn[$i]->lastInsertId();
  $conn[$i] = null;
  $i++;
}

detailsinvoice是数组,每次的ContactName都是一样的(Contactname工作只需要弄清楚循环数组)

如果有人能指出我正确的方向,我将不胜感激。

【问题讨论】:

  • 收集到该连接只能使用一次您从哪里得到这个想法?这是否意味着我们在谈论范围问题?
  • 不要$conn3设置为null,并根据需要多次使用它。
  • 您的整个请求/脚本实际上只需要 1 个连接,如果您改用 bindParam(),则可以将所有内容放在循环之前的 execute() 语句之前。你如何处理结果是另一回事,$this->InvoiceNumber 在循环之后意义不大。
  • 不需要很多mysql连接存在。您可以/应该使用相同的连接。你没有提到你面临的真正问题是什么?你只是分享了你不能做某事的假设。但没有描述您到底未能达到什么目标?

标签: php pdo sql-insert


【解决方案1】:

prepared statements的特点是你可以prepare一个语句一次然后执行多次,所以你的代码可以重写为:

// Create a connection
$conn = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );
$sql = "INSERT INTO 
        xero_invoices (ContactName, Description)
        VALUES (:ContactName, :Description)";  
// Create a statement
$st = $conn->prepare ($sql);
foreach ($detailsinvoice as $desc) { 
    // bind values and execute statement in a loop:
    $st->bindValue( ":ContactName", $this->ContactName, PDO::PARAM_STR );
    $st->bindValue( ":Description", $desc, PDO::PARAM_STR );
    $st->execute();
    $this->InvoiceNumber = $conn->lastInsertId();
}
// this is optional
$conn = null;

【讨论】:

  • 嗨,谢谢你和@RiggsFolly asnwers。一旦我看到你的两个答案,它就开始有意义了。当遇到新的东西时,我很难理解如何让它工作,但是使用你拥有的 foreach 是完全有意义的,它似乎正在做我所期望的。谢谢
【解决方案2】:

我不知道你从哪里得到一个连接只能使用一次的想法。您应该只在脚本中连接一次。然后,只要您将 $conn 变量存储并传递给您可能使用的任何函数(当然范围与此处相关),您就可以随意使用它。

// connect ONCE per script
$conn = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );

// write the query once
$sql = "INSERT INTO xero_invoices (ContactName, Description)
             VALUES (:ContactName, :Description)";  

// and prepare it once.
$st = $conn->prepare ( $sql );

// now loop over the array of parameters any number of times you like
foreach($detailsinvoice as $desc){ 

    $st->bindValue( ":ContactName", $this->ContactName, PDO::PARAM_STR );
    $st->bindValue( ":Description", $desc, PDO::PARAM_STR );
    $st->execute();

    // this line looks wrong, as $this->InvoiceNumber will get overwritten
    // each time round the loop
    //$this->InvoiceNumber = $conn->lastInsertId();

    // maybe you ment this, so at least you would have them all???? 
    $this->InvoiceNumber[] = $conn->lastInsertId();

    // or I have to assume you are going to add another query HERE
    // that will use that ID
}

prepared statement的概念是它被传递到数据库,编译,优化并保存在数据库中,几乎就像一个存储过程。

一旦准备好,就可以反复使用。您所做的就是在每次执行时将新值放入参数中。

【讨论】:

    猜你喜欢
    • 2019-07-15
    • 2018-04-06
    • 2021-11-01
    • 2014-01-25
    • 2014-01-19
    • 2014-04-30
    • 2012-03-17
    • 2015-02-28
    • 1970-01-01
    相关资源
    最近更新 更多