Perbedaan antara std :: resize (n) dan std :: shrink_to_fit di C ++?

11

Saya menemukan pernyataan ini:

resize(n)- Mengubah ukuran wadah sehingga mengandung elemen 'n'.
shrink_to_fit()- Mengurangi kapasitas wadah agar sesuai dengan ukurannya dan menghancurkan semua elemen di luar kapasitas.

Apakah ada perbedaan yang signifikan antara fungsi-fungsi ini? mereka berada di bawah vektor di c ++

Sneha Sridharan
sumber
mengubah ukuran memodifikasi ukuran wadah, shrink_to_fit tidak. Untuk penggunaan normal Anda tidak perlu tahu tentang shrink_to_fit, itu hanya tersedia untuk memungkinkan pengembang meningkatkan kinerja kode mereka secara manual.
NoSenseEtAl
2
Wadah standar memiliki ukuran dan kapasitas . Ukurannya adalah jumlah elemen saat ini dalam wadah, sedangkan kapasitasnya adalah jumlah memori yang dialokasikan (kurang-lebih). Mengubah ukuran mengubah ukuran, shrink_to_fitmengubah kapasitas.
Beberapa programmer Bung
2
Apakah Anda mengerti perbedaan antara capacitydan size?
Cubic

Jawaban:

12

Vektor memiliki dua atribut "panjang" yang memiliki arti berbeda:

  • sizeadalah jumlah elemen yang dapat digunakan dalam vektor. Ini adalah jumlah barang yang telah Anda simpan. Ini adalah panjang konseptual.
  • capacity adalah berapa banyak elemen yang sesuai dengan jumlah memori yang saat ini dialokasikan oleh vektor.

capacity >= sizeharus selalu benar, tetapi tidak ada alasan bagi mereka untuk selalu sama. Misalnya, ketika Anda menghapus suatu elemen, menyusutkan alokasi akan membutuhkan membuat alokasi baru, satu ember lebih kecil dan memindahkan isi yang tersisa ke atas ("alokasikan, pindahkan, bebas").

Demikian pula, jika capacity == sizedan Anda menambahkan elemen, vektor dapat menumbuhkan alokasi dengan satu elemen (operasi "alokasikan, pindahkan, bebas") yang lain, tetapi biasanya Anda akan menambahkan lebih dari satu elemen. Jika kapasitas perlu ditingkatkan, vektor akan meningkatkan kapasitasnya dengan lebih dari satu elemen sehingga Anda dapat menambahkan beberapa elemen lagi sebelum perlu memindahkan semuanya lagi.

Dengan pengetahuan ini, kami dapat menjawab pertanyaan Anda:

  • std::vector<T>::resize()mengubah ukuran array. Jika Anda mengubah ukurannya lebih kecil dari ukuran saat ini, objek yang berlebih dirusak. Jika Anda mengubah ukurannya lebih besar dari ukurannya saat ini, objek "baru" yang ditambahkan pada akhirnya diinisialisasi awal.
  • std::vector<T>::shrink_to_fit()meminta kapasitas untuk diubah agar sesuai dengan ukuran saat ini. (Implementasi dapat atau tidak menghormati permintaan ini. Mereka mungkin mengurangi kapasitas tetapi tidak membuatnya sama dengan ukuran. Mereka mungkin tidak melakukan apa-apa sama sekali.) Jika permintaan terpenuhi, ini akan membuang sebagian atau semua bagian yang tidak terpakai dari alokasi vektor. Anda biasanya menggunakan ini ketika Anda selesai membangun vektor dan tidak akan pernah menambahkan item lain ke sana. (Jika Anda tahu sebelumnya berapa banyak item yang akan Anda tambahkan, akan lebih baik digunakan std::vector<T>::reserve()untuk memberi tahu vektor sebelum menambahkan item apa pun daripada mengandalkan shrink_to_fitmelakukan apa pun.)

Jadi Anda gunakan resize()untuk mengubah berapa banyak barang secara konseptual dalam vektor.

Anda menggunakan shrink_to_fit()untuk meminimalkan ruang berlebih yang telah dialokasikan vektor secara internal tanpa mengubah berapa banyak barang secara konseptual dalam vektor.

cdhowie
sumber
2
Perhatikan bahwa shrink_to_fittidak semuanya atau tidak sama sekali. Suatu implementasi dapat mengurangi kapasitas bagian jalan. Sebagai contoh, pertimbangkan implementasi yang membatasi kapasitas vektor untuk kekuatan dua.
François Andrieux
5

shrink_to_fit() - Mengurangi kapasitas wadah agar sesuai dengan ukurannya dan menghancurkan semua elemen di luar kapasitas.

Itu adalah kesalahan karakteristik apa yang terjadi. Secara aman, menghancurkan semua elemen di luar bagian kapasitas tidak akurat.

Dalam C ++, ketika memori dinamis digunakan untuk objek, ada dua langkah:

  1. Memori dialokasikan untuk objek.
  2. Objek diinisialisasi / dibangun di lokasi memori.

Ketika objek dalam memori yang dialokasikan secara dinamis dihapus, ada juga dua langkah, yang mencerminkan langkah-langkah konstruksi tetapi dalam urutan terbalik:

  1. Objek di lokasi memori rusak (untuk tipe bawaan, ini adalah noop).
  2. Memori yang digunakan oleh objek tidak dapat dialokasikan.

Memori yang dialokasikan di luar ukuran wadah hanyalah penyangga. Mereka tidak memegang benda yang diinisialisasi dengan benar. Itu hanya memori mentah. shrink_to_fit()memastikan bahwa memori tambahan tidak ada tetapi tidak ada objek di lokasi tersebut. Oleh karena itu, tidak ada yang hancur, hanya memori yang tidak dapat dialokasikan.

R Sahu
sumber
2

Menurut C ++ Standard relatif terhadap shrink_to_fit

Efek: shrink_to_fit adalah permintaan tidak mengikat untuk mengurangi kapasitas () menjadi ukuran ().

dan relatif terhadap resize

Efek: Jika sz <size (), hapus ukuran terakhir () - sz elemen dari urutan. Jika tidak, tambahkan elemen sz - size () yang dimasukkan secara default ke urutan.

Jelas bahwa fungsinya melakukan hal yang berbeda. Selain itu fungsi pertama tidak memiliki parameter sedangkan fungsi kedua bahkan memiliki dua parameter. Fungsi shrink_to_fittidak mengubah ukuran wadah meskipun dapat mengalokasikan kembali memori.

Vlad dari Moskow
sumber