Berapa ukuran tumpukan yang direkomendasikan untuk SqlBulkCopy?

87

Untuk apa ukuran tumpukan yang direkomendasikan SqlBulkCopy? Saya mencari rumus umum yang dapat saya gunakan sebagai titik awal untuk penyetelan kinerja.

Jonathan Allen
sumber

Jawaban:

97

Saya memiliki utilitas impor yang berada di server fisik yang sama dengan instance SQL Server saya. Menggunakan custom IDataReader, itu mem-parsing file datar dan memasukkannya ke dalam database menggunakan SQLBulkCopy. File tipikal memiliki sekitar 6 juta baris yang memenuhi syarat, rata-rata 5 kolom desimal dan teks pendek, sekitar 30 byte per baris.

Dengan skenario ini, saya menemukan ukuran batch 5.000 sebagai kompromi terbaik dari kecepatan dan konsumsi memori. Saya mulai dengan 500 dan bereksperimen dengan yang lebih besar. Saya menemukan 5000 menjadi 2.5x lebih cepat, rata-rata, dari 500. Memasukkan 6 juta baris membutuhkan waktu sekitar 30 detik dengan ukuran batch 5.000 dan sekitar 80 detik dengan ukuran batch 500.

10.000 tidak jauh lebih cepat. Pindah ke 50.000 meningkatkan kecepatan dengan beberapa poin persentase tetapi itu tidak sebanding dengan peningkatan beban di server. Di atas 50.000 tidak menunjukkan peningkatan kecepatan.

Ini bukan rumus, tetapi ini adalah titik data lain untuk Anda gunakan.

Alric
sumber
3
Satu hal yang perlu diperhatikan adalah jika tabel kosong dan memiliki indeks. Dalam kasus tersebut, Anda mungkin ingin mengunggah semuanya dalam satu kelompok seperti yang disebutkan di sini: technet.microsoft.com/en-us/library/ms177445(v=sql.105).aspx "Jika Anda mengimpor data secara massal ke dalam tabel kosong dengan indeks dan Anda menentukan ukuran kelompok, tabel menjadi tidak kosong setelah kelompok pertama. Dimulai dengan kelompok kedua, data dicatat sepenuhnya. Untuk tabel terindeks kosong, pertimbangkan untuk melakukan impor massal dalam satu kelompok. "
Sal
SqlBulkCopy mengalirkan data dari sumber (misalnya DataTable) ke Sql jadi apa "peningkatan beban di server" yang dimilikinya pada ukuran batch yang besar? (mis. 50.000)
BornToCode
29

Ini adalah masalah yang juga telah saya selidiki. Saya ingin mengoptimalkan pengimporan file CSV yang besar (16+ GB, 65+ juta catatan, dan terus bertambah) ke dalam database SQL Server 2005 menggunakan aplikasi konsol C # (.Net 2.0). Seperti yang telah ditunjukkan oleh Jeremy , Anda perlu melakukan beberapa penyesuaian untuk keadaan khusus Anda, tetapi saya akan merekomendasikan Anda memiliki ukuran batch awal 500, dan nilai uji di atas dan di bawah ini.

Saya mendapat rekomendasi untuk menguji nilai antara 100 dan 1000 untuk ukuran batch dari posting forum MSDN ini , dan merasa skeptis. Tetapi ketika saya menguji ukuran batch antara 100 dan 10.000, saya menemukan bahwa 500 adalah nilai optimal untuk aplikasi saya. Nilai 500 SqlBulkCopy.BatchSizejuga direkomendasikan di sini .

Untuk lebih mengoptimalkan operasi SqlBulkCopy Anda, lihat saran MSDN ini ; Saya menemukan bahwa menggunakan SqlBulkCopyOptions.TableLock membantu mengurangi waktu pemuatan.

MagicAndi
sumber
Saya rasa menjalankan perintah salinan massal di server itu sendiri mungkin akan lebih cepat.
Kapten Kenpachi
16

Seperti yang dinyatakan orang lain, itu tergantung pada lingkungan Anda khususnya volume baris dan latensi jaringan.

Secara pribadi, saya akan mulai dengan mengatur BatchSizeproperti menjadi 1000 baris dan melihat bagaimana kinerjanya. Jika berhasil, maka saya terus menggandakan jumlah baris (misalnya ke 2000, 4000, dll.) Sampai saya mendapatkan waktu tunggu.

Jika tidak, jika batas waktu terjadi pada 1000, maka saya mengurangi jumlah baris hingga setengahnya (misalnya 500) hingga berhasil.

Dalam setiap kasus, saya terus menggandakan (jika berhasil) atau membagi dua (jika gagal) perbedaan antara masing-masing dari dua ukuran batch percobaan terakhir sampai menemukan sweet spot.

Faktor lain yang perlu dipertimbangkan adalah berapa lama waktu yang dibutuhkan untuk menyalin satu kumpulan baris. Batas waktu akan terjadi jika kumpulan baris yang disalin melebihi BulkCopyTimeoutproperti yang secara default adalah 30 detik. Anda dapat mencoba menggandakan BulkCopyTimeoutproperti menjadi 60 detik. Hal ini memungkinkan periode waktu yang lebih lama untuk kumpulan baris kumpulan yang lebih besar untuk disalin. Misalnya, kumpulan 50.000 baris mungkin membutuhkan waktu sekitar 40 detik, hanya melebihi batas waktu 30 detik, sehingga meningkatkannya hingga 60 detik dapat membantu kinerja.

sinar
sumber
4

Ini semua tergantung pada penerapan Anda.

Kecepatan seperti apa yang dapat Anda harapkan di jaringan Anda? Apakah Anda menggunakannya dalam Formulir atau ASP.Net? Apakah Anda perlu memberi tahu pengguna tentang kemajuan? Berapa ukuran total pekerjaan?

Dalam pengalaman saya menjalankan salinan massal tanpa ukuran batch yang ditentukan akan menyebabkan masalah waktu tunggu. Saya ingin memulai dengan sekitar 1000 rekaman dan melakukan beberapa penyesuaian dari sana.

Jeremy
sumber
Kecepatan: Bervariasi, WebForms: Ya, ASP.NET: Ya, Tabel Lebar: Ya, Tabel sempit, Ya. Ribuan baris: ya. Jutaan baris: ya. Jika Anda dapat memikirkan sebuah skenario, saya mungkin sedang melakukannya.
Jonathan Allen
1
Saya harus tetap berpegang pada jawaban saya sebelumnya. Saya tidak berpikir ada peluru perak.
Jeremy
-1

saya telah mencoba berbagai ukuran, dalam kasus saya 5000 sudah bagus

A Mustapha
sumber