Menurut pendapat saya, bahaya C ++ agak berlebihan.
Bahaya penting adalah ini: Sementara C # memungkinkan Anda melakukan operasi pointer "tidak aman" menggunakan unsafe
kata kunci, C ++ (sebagian besar merupakan superset dari C) akan memungkinkan Anda menggunakan pointer kapan pun Anda mau. Selain bahaya biasa yang melekat pada penggunaan pointer (yang sama dengan C), seperti kebocoran memori, buffer overflows, pointer menggantung, dll., C ++ memperkenalkan cara-cara baru bagi Anda untuk secara serius mengacaukan segalanya.
"Tali tambahan" ini, bisa dikatakan, yang dibicarakan oleh Joel Spolsky , pada dasarnya bermuara pada satu hal: menulis kelas yang secara internal mengelola ingatan mereka sendiri, juga dikenal sebagai " Aturan 3 " (yang sekarang dapat disebut Aturan dari 4 atau Aturan 5 di C ++ 11). Ini berarti, jika Anda ingin menulis kelas yang mengelola alokasi memorinya sendiri secara internal, Anda harus tahu apa yang Anda lakukan atau program Anda kemungkinan akan macet. Anda harus hati-hati membuat konstruktor, salin konstruktor, destruktor, dan operator penugasan, yang ternyata mudah salah, sering mengakibatkan crash aneh saat runtime.
NAMUN , dalam pemrograman C ++ setiap hari, sangat jarang memang menulis kelas yang mengelola ingatannya sendiri, sehingga menyesatkan untuk mengatakan bahwa programmer C ++ selalu harus "hati-hati" untuk menghindari jebakan-jebakan ini. Biasanya, Anda hanya akan melakukan sesuatu yang lebih seperti:
class Foo
{
public:
Foo(const std::string& s)
: m_first_name(s)
{ }
private:
std::string m_first_name;
};
Kelas ini terlihat cukup dekat dengan apa yang akan Anda lakukan di Java atau C # - ini tidak memerlukan manajemen memori eksplisit (karena kelas perpustakaan std::string
menangani semua itu secara otomatis), dan tidak ada hal "Aturan 3" yang diperlukan sama sekali sejak default salin konstruktor dan operator penugasan baik-baik saja.
Hanya ketika Anda mencoba melakukan sesuatu seperti:
class Foo
{
public:
Foo(const char* s)
{
std::size_t len = std::strlen(s);
m_name = new char[len + 1];
std::strcpy(m_name, s);
}
Foo(const Foo& f); // must implement proper copy constructor
Foo& operator = (const Foo& f); // must implement proper assignment operator
~Foo(); // must free resource in destructor
private:
char* m_name;
};
Dalam hal ini, mungkin sulit bagi pemula untuk mendapatkan penugasan, penghancur dan penyalin yang benar. Tetapi untuk sebagian besar kasus, tidak ada alasan untuk melakukan ini. C ++ membuatnya sangat mudah untuk menghindari manajemen memori manual 99% dari waktu dengan menggunakan kelas perpustakaan seperti std::string
dan std::vector
.
Masalah terkait lainnya adalah mengelola memori secara manual dengan cara yang tidak memperhitungkan kemungkinan pengecualian dilemparkan. Suka:
char* s = new char[100];
some_function_which_may_throw();
/* ... */
delete[] s;
Jika some_function_which_may_throw()
benar - benar melempar pengecualian, Anda kehabisan memori karena memori yang dialokasikan untuk s
tidak akan pernah direklamasi. Tetapi sekali lagi, dalam prakteknya ini bukan masalah lagi karena alasan yang sama bahwa "Aturan 3" tidak terlalu menjadi masalah lagi. Sangat jarang (dan biasanya tidak perlu) untuk benar-benar mengelola memori Anda sendiri dengan pointer mentah. Untuk menghindari masalah di atas, semua yang perlu Anda lakukan adalah menggunakan std::string
atau std::vector
, dan destruktor secara otomatis akan dipanggil selama tumpukan dibatalkan setelah pengecualian dilemparkan.
Jadi, tema umum di sini adalah banyak fitur C ++ yang tidak diwarisi dari C, seperti inisialisasi / penghancuran otomatis, copy constructor, dan pengecualian, memaksa programmer untuk ekstra hati-hati ketika melakukan manajemen memori manual dalam C ++. Tetapi sekali lagi, ini hanya masalah jika Anda berniat untuk melakukan manajemen memori manual di tempat pertama, yang hampir tidak pernah diperlukan lagi ketika Anda memiliki kontainer standar dan smart pointer.
Jadi, menurut saya, sementara C ++ memberi Anda banyak tali tambahan, hampir tidak pernah perlu menggunakannya untuk menggantung diri, dan perangkap yang dibicarakan Joel mudah untuk dihindari dalam C ++ modern.
Your questions should be reasonably scoped. If you can imagine an entire book that answers your question, you’re asking too much.
. Saya percaya ini memenuhi syarat sebagai pertanyaan seperti itu ...