Tôi không nghĩ Zend_Db hỗ trợ chèn nhiều hàng.
Nhưng nếu bạn chỉ có hai hàng hoặc nhiều hơn một chút, bạn chỉ có thể sử dụng vòng lặp.
foreach ($data as $row)
{
$db->insert('table', $row)
}
Bill Karwin, một cựu phát triển Zend Framework, viết
this on Nabble some time ago:
Rowsets cơ bản là một đối tượng thu, vì vậy tôi sẽ thêm các phương pháp để lớp đó để cho phép hàng để được thêm vào các thiết lập. Vì vậy, bạn sẽ có thể thực hiện việc này:
// creates a rowset collection with zero rows
$rowset = $table->createRowset();
// creates one row with unset values
$row = $table->createRow();
// adds one row to the rowset
$rowset->addRow($row);
// iterates over the set of rows, calling save() on each row
$rowset->save();
Không có ý nghĩa gì khi chuyển một số nguyên để tạoRowset() để tạo N hàng trống. Bạn sẽ chỉ phải lặp qua chúng để điền chúng với các giá trị. Vì vậy, bạn cũng có thể viết một vòng lặp để tạo và điền các hàng riêng lẻ với dữ liệu ứng dụng, sau đó thêm chúng vào bộ sưu tập.
$rowset = $table->createRowset();
foreach ($appData as $tuple)
{
$row = $table->createRow($tuple);
$rowset->addRow($row);
}
$rowset->save();
Sẽ có ý nghĩa khi cho phép mảng mảng được chuyển đến createRowset(), vì điều này phù hợp với việc sử dụng một bộ tuple để createRow().
$rowset = $table->createRowset($appData); // pass array of tuples
Điều này sẽ thực hiện cùng một vòng lặp như ví dụ trước ở trên (trừ lưu() ở cuối), tạo một hàng mới của hàng mới, sẵn sàng để lưu() d.
Có hai cách trong SQL để nâng cao hiệu quả chèn dữ liệu:
Sử dụng một câu lệnh INSERT duy nhất với nhiều hàng:
INSERT INTO t (col1, col2, col3) VALUES (1, 2, 3), (4, 5, 6), (7, 8, 9);
Chuẩn bị một câu lệnh INSERT và thực hiện nó nhiều lần:
CHUẨN BỊ INSERT INTO t (col1, col2, col3) GIÁ TRỊ; (,,??) EXECUTE 1, 2, 3 EXECUTE 4, 5, 6 EXECUTE 7, 8, 9
Tuy nhiên, việc hỗ trợ một trong những cải tiến này sẽ thêm phức tạp cho các lớp Row và rowSet. Điều này là do cách nội bộ lớp Zend_Db_Table_Row hiện tại phân biệt giữa một hàng cần được INSERTed hoặc UPDATEd khi bạn gọi save().Sự khác biệt này được đóng gói bởi đối tượng Row, do đó Rowset không biết các hàng riêng lẻ có là các hàng mới hay các bản sao đã sửa đổi của các hàng hiện có hay không. Do đó đối với lớp Rowset để cung cấp phương thức save() nhiều hàng sử dụng SQL hiệu quả hơn, việc quản lý dữ liệu bẩn sẽ phải được tái cấu trúc hoàn toàn. Các giải pháp dễ dàng hơn là cho Rowset để lặp qua các hàng của nó, gọi save() trên mỗi hàng. Điều này là tốt hơn cho việc đóng gói OO, mặc dù nó không giúp tối ưu hóa SQL để chèn một rowset.
Trong mọi trường hợp, rất hiếm khi tải hàng loạt dữ liệu hàng loạt trong một yêu cầu web điển hình, khi có nhu cầu lớn nhất về SQL hiệu quả. Sự khác biệt về hiệu quả cho một số lượng nhỏ các hàng nhỏ, do đó, nó sẽ là một cải tiến đáng chú ý chỉ khi bạn đang tải hàng loạt số lượng lớn hàng. Nếu đó là trường hợp, bạn không nên sử dụng INSERT anyway, bạn nên sử dụng MySQL LOAD DATA tuyên bố, hoặc tính năng tương đương nếu bạn sử dụng một thương hiệu RDBMS. INSERT thường không phải là lựa chọn hiệu quả nhất để tải nhiều dữ liệu.
Về việc trả lại tự động tạo khóa, tôi sẽ không bận tâm. Lưu ý rằng nếu bạn sử dụng SQL đơn giản (ví dụ như trong CLI mysql) và bạn chèn nhiều hàng trong một câu lệnh INSERT, bạn chỉ có thể nhận được giá trị id được tạo cuối cùng, chứ không phải giá trị id cho tất cả các hàng được chèn vào. Đây là hành vi SQL; nó là đúng cho bất kỳ ngôn ngữ hoặc khuôn khổ nào.
INSERT INTO t (col1, col2, col3) VALUES (1, 2, 3), (4, 5, 6), (7, 8, 9);
SELECT LAST_INSERT_ID(); -- returns only the id for the third tuple
Nếu bạn cần id cho mỗi hàng, bạn nên viết vòng lặp và chèn từng hàng một, truy xuất id được tạo sau mỗi hàng được chèn.
Các đa chèn yêu cầu tính năng trong Zend 2.0 ([ZF2-475] (http://framework.zend.com/issues/browse/ZF2-475)) đã bị đóng dưới dạng wontfix. – Tgr