[Powered by Google Translate] [Minggu 4, Lanjutan] [David J. Malan - Universitas Harvard] [Ini adalah CS50. - CS50.TV] Ini adalah CS50, dan ini adalah akhir minggu 4. Jadi beberapa kabar baik dan kabar buruk. Tidak ada kuliah pada hari Senin, tidak ada masalah ditetapkan minggu depan. [Siswa bersorak] Anda tidak akan menyukai mana hal ini terjadi. Tapi kita memiliki ini sebagai gantinya Rabu depan, dan ada juga per kuliah 1 silabus Jumat depan Jumat sehingga kita bisa tetap di jalur. Tapi semuanya akan difilmkan seperti biasa, jadi tidak perlu khawatir. Dan berkaitan dengan kuis 0 yang akan kita lakukan menjelang akhir minggu adalah posting di cs50.net homepage kursus ini penjelasan macam apa harapan Anda harus memiliki ketika datang ke kuis pertama. Secara umum, itu akan menjadi pilihan ganda, benar-salah, jawaban singkat, masalah coding pendek. Kau tidak akan diharapkan untuk melaksanakan setara dengan dari masalah yang Anda akan lihat di pset, untuk yang Anda memiliki komputer dan debugger dan sejenisnya, tetapi akan ada masalah coding kecil. Dan memang, panduan terbaik untuk mendapatkan rasa apa CS50 kuis seperti adalah pergi ke cs50.net, pergi ke link Kuis, dan Anda dapat melihat beberapa tahun terakhir senilai kuis. Hanya menyadari bahwa kurikulum tidak selalu sama selama bertahun-tahun. Kadang-kadang kita tambahkan, kadang-kadang mengurangi, jadi jika Anda melihat beberapa topik pada salah satu dari orang-orang tua kuis bahwa Anda tidak tahu apa yang dibicarakan, itu baik bahwa kita menutupinya atau bahwa kita tidak menutupinya. Namun dalam bentuk ulasan, ini hari Minggu, Senin, dan Selasa serta sesi kursus-lebar review pada Minggu malam - waktu dan lokasi akan diumumkan pada homepage kursus ini - Anda semua memiliki kesempatan untuk meninjau dengan rekan-rekan mengajar kursus ini bahan untuk tahun ini, baik dalam bagian dan sebagai kelas penuh, dan mereka akan difilmkan seperti biasa juga. Baiklah. Jadi tanpa basa-basi lagi, satu komentar pada lulus / gagal dan add / drop. Anda mungkin telah melihat catatan saya tadi malam, dan ini benar-benar hanya beberapa kepastian tambahan bahwa jika Anda termasuk orang yang sangat kurang nyaman atau di suatu tempat di antara dan Anda merasa hanya sedikit di atas kepala Anda, menyadari bahwa memang cukup normal, dan ada struktur dukungan yang cukup di tempat, salah satunya jam kantor berniat meningkatkan semua lebih per malam email terakhir saya, dan menyadari juga bahwa pilihan seperti lulus / gagal untuk kelas seperti ini benar-benar dimaksudkan sebagai mekanisme untuk mengambil tepi off dari kursus seperti ini, sehingga lagi jika Anda menghabiskan mereka 10, 15, 20 jam hanya mencoba untuk mendapatkan beberapa pset untuk bekerja dan Anda tahu bahwa Anda 90-95% dari perjalanan ke sana tetapi Anda tidak dapat menemukan beberapa bug sialan, dalam lulus / gagal Model yang semacam apa-apa. Idenya adalah bahwa dengan mekanisme yang Anda kemudian dapat pergi fokus pada psets lain atau tidur atau apa pun yang Anda ingin fokus pada. Jadi menyadari bahwa Anda telah sampai Selasa ini datang - teknis Senin 5th, tapi itu hari libur, jadi ini Selasa mendatang - untuk beralih dari lulus / gagal versa dinilai atau sebaliknya. Dan jika Anda benar-benar di tebing dan berpikir untuk menjatuhkan sama sekali, mohon menangkap saya setelah kuliah atau drop me catatan. Kami akan senang untuk setidaknya chatting sebelum Anda tawaran kata perpisahan. Baiklah. Jadi kita mulai mengambil roda pelatihan off terakhir kali. Secara khusus, kami fokus pada string. String adalah sesuatu yang dideklarasikan pada perpustakaan CS50, khusus dalam file bernama cs50.h yang kita akan mulai melihat minggu ini dan berikutnya. Tapi string adalah benar-benar hanya penyederhanaan sesuatu itu sedikit lebih arcanely digambarkan sebagai char *. Char kita akrab dengan. Ini hanya satu karakter. Tapi * pada Senin dilambangkan apa? >> [Mahasiswa] pointer. Sebuah pointer. Dan apa pointer? >> [Mahasiswa] Sebuah alamat. Ini seperti alamat, lokasi di memori. Apa alamat atau lokasi atau memori? Sekali lagi, kita semua memiliki laptop dengan pertunjukan atau 2 gigabyte RAM kemungkinan besar hari ini, dan itu berarti Anda memiliki miliar atau 2 milyar byte senilai memori. Dan itu tidak terlalu penting apa yang secara fisik terlihat seperti, tetapi mengambil pada iman bahwa Anda dapat menomori semua byte individu yang memiliki laptop Anda sendiri - ini adalah byte 0, ini adalah byte 1, ini adalah byte 2 miliar - dan itulah apa komputer tidak. Bila Anda mengalokasikan ruang untuk satu karakter, misalnya, itu jelas harus tinggal di suatu tempat di memori komputer Anda, dan mungkin itu di nomor 12345 byte, dan itu di suatu tempat di sini dalam memori komputer Anda. Dan alamat maka karakter yang 12345. Sekarang, dalam seminggu 0 sampai sekarang sejauh ini, kami belum benar-benar peduli dimana dalam hal memori disimpan karena kita biasanya menggunakan simbol, variabel, dan array untuk benar-benar mendapatkan data kami. Tapi pada hari Senin dan semua lebih hari ini, Anda sekarang akan memiliki semua lebih ekspresif kemampuan menulis dengan program untuk benar-benar memanipulasi memori komputer namun Anda lihat cocok, baik untuk tujuan yang baik dan buruk, bug menjadi hasil yang sangat umum pada saat ini dalam belajar hal-hal ini. Tapi apa benar-benar berarti menjadi char *? Mari kita lanjutkan kembali ke - dan kami akan kembali ke Binky seperti yang dijanjikan hari ini. Mari kita pergi ke sebuah contoh sederhana di sini. Mari saya simpan file ini sebagai compare.c, dan biarkan aku hanya mendapatkan beberapa kode template di sini sehingga termasuk stdio.h, saya juga memberi diriku termasuk cs50.h. Saya akan memperbesar sana. Mari saya mulai menulis int main, main (void), dan sekarang saya ingin melakukan sesuatu seperti ini: printf ("Beri aku string:") dan kemudian saya akan menggunakan s string yang akan GetString untuk mendapatkan string dari pengguna, maka aku akan meminta pengguna untuk satu. ("Beri aku string lain:") dan aku akan meminta mereka melalui GetString untuk mendapatkan itu. Saya akan menyebutnya t karena t datang setelah s dan s adalah nama yang bagus untuk string jika itu cukup generik. Jadi GetString, dan sekarang saya hanya ingin melakukan cek kewarasan dan aku akan mengatakan if (s == t) maka aku hanya akan memberitahu pengguna printf ("Anda mengetik hal yang sama \ n"); lagi aku akan mencetak sesuatu seperti ("Anda mengetik sesuatu yang berbeda \ n!") atau apa pun kalimat akan. Jadi sesuatu seperti itu. Lalu seperti biasa, saya akan kembali 0 yang hanya menandakan bahwa tidak ada hal buruk terjadi, dan aku akan pergi ke depan dan mengkompilasi dan menjalankan program ini. Tetapi pada hari Senin kami berlari program ini, dan benar-benar diberitahu bahwa HELLO tidak HELLO GOODBYE dan tidak GOODBYE. Perilaku kita lihat adalah sedikit lebih seperti ini. Biarkan aku pergi ke direktori sumber saya, zoom di sini, dan mari kita lakukan membuat bandingkan. Disusun oke. Biarkan saya jalankan membandingkan. Beri aku string: HELLO. Beri aku string lain: HELLO. Anda mengetik sesuatu yang berbeda! Nah, biarkan aku mencoba sesuatu yang sederhana seperti 50, 50. Anda mengetik sesuatu yang berbeda! hi, hi. Jadi jelas, ada sesuatu yang terjadi di sini. Tapi apa adalah penjelasan mengapa? Rupanya, baris 12 adalah benar-benar disfungsional. Apa masalah mendasar di sini? Ya. >> [Mahasiswa] Ini membandingkan alamat. Ya, tepatnya. Ini benar-benar membandingkan alamat di mana HELLO HELLO dan disimpan. Ini tidak membandingkan surat HELLO lagi dan lagi, karena apa yang sebenarnya terjadi, selama ini kita telah menggunakan GetString - Papan ini lagi memori komputer kita, dan katakanlah saya sebut GetString setelah mendeklarasikan variabel s. Apa memori saya terlihat seperti? Mari kita sewenang-wenang mengatakan bahwa s terlihat seperti ini. Ini persegi. Dan cukup banyak setiap saat saya sudah ditarik sepotong memori pada layar jika 32 bit saya sudah menggambar kotak seperti ini karena memang di alat, pointer, alamat, adalah 32 bit. Ini sama dengan int. Yang dapat bervariasi berdasarkan pada sistem komputer. Bagi Anda yang samar-samar akrab dengan fakta bahwa Anda Mac atau PC adalah 64 bit, yang benar-benar menunjukkan bahwa komputer Anda menggunakan 64-bit pointer, 64-bit alamat, dan di antara upsides itu adalah komputer Anda dapat memiliki RAM lebih dari tadi. Singkat cerita, kembali pada hari ketika komputer hanya digunakan 32 bit untuk mewakili alamat, jumlah terbesar byte Anda bisa mewakili dalam hal ini adalah bagaimana jika Anda memiliki 32 bit? Jadi 4 miliar, benar, karena 2 ke 32 adalah 4 miliar. Jumlah ini telah berulang dalam kursus. Jadi jika Anda hanya memiliki 32 bit, jumlah tertinggi Anda bisa menghitung sampai kira-kira 4 miliar. Tapi itu keterbatasan mendasar dari komputer sampai beberapa tahun yang lalu karena jika Anda hanya dapat menghitung setinggi 4 miliar, tidak masalah jika Anda membeli 8 gigabyte RAM atau bahkan 5 gigabyte RAM; Anda tidak dapat menghitung yang tinggi, sehingga itu tidak berguna. Anda hanya bisa mengakses 3 atau 4 gigabyte pertama memori komputer Anda. Itu kurang dari sebuah isu sekarang, dan Anda dapat membeli MacBook Pro dan Dells dengan 8 gigabyte RAM atau bahkan lebih hari ini. Tapi jika saya mengalokasikan cukup hanya dalam program ini pointer, pointer yang disebut s, mungkin terlihat seperti ini di layar karena memang kita perlu mengupas lapisan ini. Saya menyimpan string mengatakan, tetapi pada hari Senin, string adalah benar-benar * char, alamat beberapa karakter. Jadi mari kita bahwa roda pelatihan di luar meskipun kita akan terus menggunakan GetString untuk saat ini. Jadi saya sudah menyatakan s, dan ini adalah sepotong memori, 32 bit. Apa yang ada di sini di memori secara default? >> [Respon siswa tidak terdengar] Apa itu? >> [Mahasiswa] Sampah. >> Sampah. Tepat. Jika Anda programmer tidak memasukkan nilai dalam variabel, yang tahu apa itu? Kadang-kadang Anda beruntung dan itu 0, yang merupakan jenis nilai, standar yang baik, bersih, tapi seperti yang kita lihat Senin, kadang-kadang omong kosong, beberapa nomor positif atau negatif sangat besar yang berasal dari mana? Ya. >> [Mahasiswa] Fungsi sebelumnya. >> Ya. Seringkali fungsi yang dipanggil sebelumnya karena ingat, ketika Anda memanggil fungsi-fungsi dalam memori, mereka mengambil ruang lebih banyak dan lebih dari bawah ke atas, dan segera setelah kembali fungsi, memori yang akan digunakan kembali oleh orang berikutnya yang dipanggil, yang menggunakan slice yang sama Anda memori. Dan jika Anda sudah sampah kiri ada, nilai sebelumnya, kita mungkin keliru s sebagai memiliki beberapa nilai ketika benar-benar kita tidak menaruh apa pun di sana. Jadi RAM kami di titik ini terlihat seperti ini. Sekarang di sisi kanan baris 7 kita memanggil GetString, yang telah kita lakukan sekarang untuk minggu, tapi apa yang benar-benar melakukan GetString? GetString ditulis oleh staf CS50 adalah sedikit cerdas di bahwa segera setelah pengguna mulai mengetik tombol Enter dan hits, GetString angka keluar berapa banyak keystrokes melakukan hit pengguna, berapa banyak karakter yang saya perlukan untuk mengalokasikan RAM untuk. Dan di mana RAM yang berasal dari, siapa tahu? Ini suatu tempat di komputer Anda 2 gigabyte atau entah apa lagi memori. Tapi anggap bahwa komputer menemukan ruang untuk kata HELLO di sini. Kata saya mengetik adalah H-E-L-L-O. Dan jika kita menggambar ini sebagai rangkaian karakter, kita mungkin menarik seperti ini. Tapi aku perlu melakukan 1 hal ekstra. Apa yang menjadi milik pada akhir setiap string dalam C? Karakter nol, yang kita tulis sebagai \ 0. Secara teknis angka 0, tetapi backslash membuat semua semakin jelas bahwa ini adalah benar-benar angka 0, 0 integer; itu tidak, untuk 0 misalnya, kutipan-tanda kutip yang Anda mungkin mengetik di keyboard. Jadi ini adalah HELLO. Dan apa yang kita katakan pada hari Senin bahwa fungsi seperti GetString sebenarnya kembali semua minggu? Ini tidak kembali string per se karena itu tidak benar-benar memiliki makna karena string tidak ada. Mereka semacam fabrikasi di perpustakaan CS50. Apa benar-benar string, lebih teknis? >> [Mahasiswa] Ini karakter pertama. Tepat. Ini cukup sederhana alamat dari karakter pertama bahwa pengguna diketik masuk Jadi, jika kata-kata saya HELLO berakhir itu di nomor 123 byte dan kemudian di nomor 124 byte, 125, 126, dan sebagainya, jika saya hanya nomor byte saya dari 0 ke atas, apa yang sebenarnya GetString adalah kembali secara harfiah nomor 123. Jadi apa yang akan dimasukkan ke dalam s adalah nomor 123, bukan huruf H, bukan kata HELLO, cukup hanya alamat di mana saya dapat menemukan huruf pertama dari HELLO. Tapi itu tidak tampak seperti cukup. Saya meminta Anda untuk string, bukan karakter. Jadi bagaimana kita atau komputer tahu bahwa ELLO jenis datang bersama dengan H? Apa jenis perjanjian yang kita miliki? Ya. [Mahasiswa] Ini terus mengatakan dirinya menemukan karakter lagi. >> Tepat. Ada konvensi ini manusia-komputer dimana ketika Anda berurusan dengan string, atau dikenal sekarang sebagai bintang char, Anda hanya perlu mencari tahu di mana akhir dari setiap string dalam hidup adalah dengan benar-benar hanya iterasi di atasnya dengan untuk loop, while loop, apa pun, sehingga ketika Anda menemukan akhir string sekarang Anda dapat menyimpulkan dari itu, oh, seluruh kata itu HELLO. Bagi Anda dengan pengalaman pemrograman sebelumnya mungkin tahu di Jawa Anda hanya bisa menelepon dan panjang. dalam bahasa lain Anda dapat menghubungi panjang atau mirip. Itu karena dalam banyak bahasa, terutama hal-hal yang disebut bahasa berorientasi objek, panjang dari sesuatu adalah jenis dalamnya dikemas dari sepotong data itu sendiri, banyak seperti kita dikemas ID dan nama dan rumah dalam seorang mahasiswa pada hari Senin. Tapi C adalah tingkat yang lebih rendah. Tidak ada benda atau kelas, jika Anda pernah mendengar istilah itu sebelumnya. Yang harus benar-benar alamat memori. Jadi ini adalah semacam cara kuno mewakili struktur menarik data. Anda memiliki nilai awal seperti alamat karakter pertama dan kemudian hanya beberapa konvensi sewenang-wenang yang semua orang setuju untuk mengikuti. Jadi bagaimana panjang string diimplementasikan, apakah kita usulkan? Strlen, strlen, yang sebagian dari Anda sekarang telah digunakan beberapa kali. Ini cukup sederhana, kan? Ini seperti 2 baris kode. Hal ini cukup banyak loop untuk dari beberapa macam, mungkin dengan variabel lokal tambahan. Tapi strlen hanya harus mengambil pointer dan kemudian mulai mencari \ 0. Dan secepat itu menemukan, itu bisa mengembalikan jumlah langkah yang diambil itu dalam string tersebut. Jadi kita dapat menyimpulkan dari ini apa yang terjadi di depan. Misalkan maka saya menyatakan t seperti yang telah saya lakukan di baris 10. Ini adalah beberapa nilai sampah. Siapa tahu pada awalnya? Tapi di sisi kanan garis 10 Saya menelepon GetString lagi. Siapa yang tahu di mana ini berakhir? Mari kita sewenang-wenang mengatakan bahwa sistem operasi menemukan ruang untuk itu cara di atas sini. Saya kebetulan kebetulan ketik H-E-L-L-O lagi, dan sehingga kita dapat menarik jenis yang sama gambar. Tapi fakta bahwa saya sudah digambar ulang gambar ini disengaja karena itu adalah berbeda HELLO dari satu ini. Jadi di sini ini mungkin lokasi 456, ini adalah 457, dan sebagainya. Jadi apa yang akan ditaruh dimana tanda tanya dulu? Dalam kasus ini 456. Kami memilih angka-angka ini sewenang-wenang karena benar-benar setelah hari ini kita tidak akan peduli begitu banyak tentang apa alamat apa pun. Yang kami pedulikan adalah bahwa kita dapat mengetahui alamat dari beberapa bagian dari data seperti HELLO. Jadi benar-benar apa yang kebanyakan orang lakukan dalam ilmu komputer ketika berbicara tentang alamat memori dan berbicara tentang pointer khusus, daripada repot-repot mencari tahu 123 - siapa yang peduli di mana hal ini sebenarnya, kita hanya tahu bahwa itu adalah di beberapa alamat numerik - kita menyederhanakan dunia dan hanya mengatakan bahwa s menunjuk ke karakter yang dan t menunjuk ke karakter itu. Dan fakta bahwa itu panah cukup disengaja karena secara harfiah sekarang s menunjuk H dan t menunjuk pada H lain karena pada akhir hari, tidak peduli apa alamat tersebut, tetapi tidak peduli bahwa kita memiliki kemampuan untuk mengekspresikan alamat bahwa dengan beberapa potongan kode. Kami belum benar-benar dimanipulasi alamat ini dulu jadi kita akan melihat di mana kita dapat menyisipkan dan semacam melakukan hal-hal dengan pointer, tapi untuk saat ini sejalan 12 harfiah nilai-nilai apa yang kita membandingkan menurut cerita ini sejalan 12? Kami katakan adalah 123 sama sama dengan 456? Dan itu pasti tidak terjadi. Dan bahkan secara konseptual, pointer ini jelas tidak sama dengan ini karena Anda disebut GetString dua kali, dan GetString tidak mencoba untuk menjadi super pintar, tidak mencoba untuk menyadari, oh, Anda ketik HELLO 5 menit lalu; izinkan saya memberi Anda pointer yang sama seperti yang kuberikan padamu sebelumnya, itu hanya mengalokasikan sepotong memori baru setiap kali Anda menyebutnya. Jadi bagaimana kita mengatasi masalah ini? Jika tingkat yang lebih tinggi saya ingin membandingkan string HELLO dan HELLO - Saya tidak peduli tentang pointer - bagaimana aku pergi tentang menjawab pertanyaan, apakah pengguna ketik hal yang sama? Apa yang diperlukan di sini? Ya. [Mahasiswa] Gunakan fungsi. >> Saya dapat menggunakan fungsi keluar dari kotak. Saya bisa menggunakan fungsi yang disebut strcmp, s-t-r-c-m-p, hanya versi singkat mengatakan string yang dibandingkan. Dan jika kita masuk ke, misalnya, membandingkan 2, yang merupakan salah handout hari ini, Saya melakukan hal itu. Aku terus segala sesuatu yang lain sama dari baris 1 pada turun ke 26 atau lebih, dan sekarang perhatikan bagian ini telah berubah hanya sedikit. Mari kita mengabaikan baris 28 sejenak dan fokus hanya pada satu ini. Apa yang kita katakan Senin bahwa membandingkan str tidak? Ini menangani proses mengambil 2 pointer, s dan t dalam hal ini, semacam hampir meletakkan jari pada orang-2 surat, dan apa yang harus Anda lakukan adalah sesuatu seperti loop sementara atau untuk loop, dan mengatakan orang-sama? Jika demikian, bergerak jari atau pointer ke depan. Apakah ini sama, sama, ini sama, ini sama, ini sama? Dan ooh, aku di akhir string di kedua s dan t. Saya belum menemukan kontradiksi. Ya, string ini adalah sama. Dan apa str membandingkan kembali jika string 2 adalah sama, rupanya? Nol. Jadi 0 adalah baik dalam hal ini karena jika ia mengembalikan -1 atau +1, yang berarti bahwa itu hanya terjadi untuk datang sebelum t abjad atau setelah t. Dan mengapa itu berguna untuk memiliki fungsi yang memberitahu anda string mana yang datang sebelum atau setelah dalam kamus? [Mahasiswa] Pencarian. Pencarian >> dan menyortir. Sehingga Anda dapat melakukan hal-hal seperti pencarian biner atau bubble sort atau menggabungkan semacam di mana Anda harus membandingkan hal. Sejauh ini kita sudah seperti memotong beberapa sudut dan hanya berbicara tentang pemilahan dalam konteks angka karena itu bagus dan mudah untuk berbicara tentang, tetapi Anda pasti dapat membandingkan string, apel dan pisang, karena jika apel diketahui datang sebelum pisang, sama, Anda dapat memindahkan string di dalam memori seperti Rob lakukan dengan gabungan semacam dalam video dan kita lakukan di sini di atas panggung dengan semacam seleksi, insertion sort, dan bubble sort. Jadi di mana lagi bisa kita ambil ini? Mari kita coba ini. Semacam Mari kita lupakan tentang pelajaran itu untuk beberapa saat dan coba sekarang dan menyalin 1.c untuk melakukan hal berikut. Sejalan 21 Saya mengatakan sesuatu cetak, maka aku mendapatkan string dari user, maka aku memeriksa ini. Kami belum benar-benar masuk ke kebiasaan ini, tapi mari kita sekarang melakukan hal ini. Mari kita benar-benar mengupas lapisan ini. Ini benar-benar char *. Orang ini benar-benar char *. Jadi apa artinya untuk memeriksa apakah s == NULL? Ternyata bahwa ketika Anda memanggil fungsi seperti GetString atau lebih umum hanya meminta komputer untuk memberikan beberapa memori, sesuatu yang bisa salah. Anda bisa menjadi gila dan meminta komputer untuk terabyte memori dengan meminta triliunan byte memori yang hanya tidak ada di komputer, namun fungsi GetString dan lainnya perlu beberapa cara berteriak pada Anda jika Anda sudah meminta terlalu banyak. Dan cara GetString melakukan ini adalah jika Anda telah meminta lebih banyak memori daripada yang tersedia di komputer, bahkan jika itu super, super rendah probabilitas karena tidak satupun dari kita akan mengetik satu triliun karakter dan kemudian tekan Enter, tetapi probabilitas rendah meskipun mungkin, saya masih ingin memeriksa untuk itu berjaga-jaga, dan nilai khusus yang GetString, jawaban, dan fungsi lainnya kembali jika sesuatu yang tidak beres adalah NULL dalam semua topi. Dan apa yang NULL? NULL hanya begitu terjadi untuk mewakili pointer. Ini memori 0 address. Dunia memutuskan bahwa sewenang-wenang, jika ini adalah memori komputer saya - Anda tahu apa? - kita akan mencuri hanya 1 byte dari memori setiap komputer, dan ini adalah lokasi 0. Kita akan memberikan julukan NULL, dan kita akan berjanji bahwa kita tidak akan pernah benar-benar menempatkan data nyata ada karena kita hanya perlu sewenang-wenang nilai khusus, 0, alias NULL, sehingga kita bisa berteriak pengguna jika terjadi kesalahan. Jika tidak, Anda mungkin tidak tahu apakah 0 berarti menempatkan sesuatu di sini atau apakah itu berarti ada yang tidak beres? Kita harus semua setuju bahwa tidak berarti NULL dikembalikan, ada alamat yang sebenarnya dikembalikan. Sekarang, di sini aku hanya mengadopsi konvensi manusia saya saya kembali 1 dari main jika terjadi kesalahan. Itu karena konvensi kembalinya utama adalah untuk kembali 0 jika baik, 1 atau beberapa nilai lain jika buruk. Tapi GetString dan setiap fungsi yang berhubungan dalam mengembalikan memori NULL jika sesuatu berjalan buruk. Oke. Jadi, sayangnya, jalur 27, super sederhana meskipun, benar-benar gagal untuk menyalin string. Kenapa? Kita bisa melihat ini sebagai berikut. Saya mengklaim sejalan 27 akan membuat salinan s dan menyebutnya t. Jadi aku tidak meminta pengguna untuk 2 string saat ini, aku hanya mengatakan nilai dalam s harus dimasukkan ke dalam t juga. Jadi sekarang hanya untuk menunjukkan bagaimana rusak ini, sejalan 29 seterusnya apa yang saya lakukan? Pertama saya memeriksa apakah panjang t lebih besar dari 0. Ada beberapa string sana. Pengguna mengetik sesuatu masuk Apa baris 32 dilakukan, rupanya? [Respon siswa terdengar] Kanan >>. Anda dapat menyimpulkan jenis itu dari apa yang saya katakan itu melakukan. Tapi secara teknis, apa ini lakukan? t [0] mewakili apa? [Mahasiswa] Karakter zeroth. >> [Malan] Karakter zeroth. Atau, lebih mirip manusia, karakter pertama di t, apa pun itu, H mungkin dalam kasus ini. Dan toupper melakukan apa yang dikatakannya. Ini mengkapitalisasi karakter zeroth dari t dan perubahan itu. Jadi ini berarti mengambil karakter ke nol dari t, membuatnya huruf besar, dan dimasukkan kembali ke dalam lokasi yang sama. Jadi jika saya ketik halo dalam huruf kecil, ini harus mengubah h huruf kecil ke H. modal Tapi masalahnya adalah bahwa dalam garis 35 dan 36 apa yang saya lakukan adalah mencetak bagi kita s dan t. Dan apa dugaan Anda? Apa yang saya benar-benar akan melihat apakah saya mengetik di halo dalam huruf kecil semua? Apa yang akan mendapatkan dicetak? >> [Respon siswa terdengar] >> Apa itu? [Mahasiswa] Big H dan sisanya kecil. >> The H besar dan sisanya kecil yang, s atau t? [Mahasiswa] Kedua. Keduanya >>. Tepat. Jadi mari kita lihat apa yang terjadi di sini. Biarkan aku pergi ke depan dan kompilasi ini. Ini adalah copy1, sehingga membuat copy1. Baiklah. Zoom in Biarkan aku pergi ke depan dan menjalankan copy1, Enter, Katakan sesuatu: halo dalam huruf kecil. Ini dikapitalisasi copy, tapi rupanya dikapitalisasi asli juga, karena apa yang sekarang terjadi dalam cerita ini? Sejalan 27 Saya tidak benar-benar tampaknya menyalin string, tapi meskipun Anda mungkin intuitif berharap bahwa akan terjadi, jika Anda berpikir tentang gambar ini, apa yang sebenarnya telah saya lakukan? Setengah dari gambar yang sama. Jadi mari kita memutar kembali dalam waktu sehingga t belum ada dalam cerita. S bisa eksis dalam cerita, tapi mari kita huruf kecil halo saat ini. Jadi biarkan saya memperbaiki apa yang saya benar-benar diketik masuk Dalam hal ini di sini kita memiliki h-e-l-l-o. Kami akan menggambar sebagai urutan karakter, memasang garis pemisah saya di sini dan \ saya 0. Jadi ini adalah di mana kita secepat baris 1 sampai 24-ish, memberi atau mengambil, telah dieksekusi. Ini adalah gambar dari ingatanku. Ketika saya sampai ke baris 27, apa yang terjadi? Sama seperti sebelumnya, saya mendapatkan pointer, yang saya akan menarik sebagai alun-alun ini. Ini disebut t. Dan apa nilainya secara default? Siapa yang tahu? Beberapa nilai sampah. Jadi saya akan abstrak yang jauh sebagai tanda tanya. Dan segera setelah sisi kanan baris 27 mengeksekusi, apa yang saya meletakkan dalam t? Hal yang sama yang ada di s. Jadi jika kita sejenak menghapus abstraksi panah dan kita katakan, oh, ini adalah memori beban alamat 123, ketika Anda mengatakan t mendapat s, titik koma, Anda benar-benar menempatkan 123 di sini. Sekarang jika kita jenis menyederhanakan dunia kita lagi dengan gambar, apa yang telah Anda benar-benar dilakukan hanya menambahkan panah lain untuk dunia Anda yang menunjuk dari t ke string yang sama persis. Jadi ketika di baris 31 dan 32 saya benar-benar pergi tentang mengubah t [0], apa yang t [0] tampaknya identik dengan sekarang? s [0] Jadi itulah semua yang terjadi. Dan meskipun semacam ini terasa dari tingkat rendah kecil dan misterius dan ini semacam terasa seperti mungkin intuitif ini seharusnya hanya bekerja - Saya telah membuat salinan dari hal-hal sebelum dan itu hanya bekerja - jika Anda benar-benar berpikir tentang apa string benar-benar, itu adalah char *. Nah, apa itu? Ini alamat beberapa karakter. Maka mungkin akan lebih masuk akal bahwa ketika Anda mencoba untuk melakukan sesuatu Super tampaknya sederhana seperti ini, semua yang Anda lakukan adalah menyalin alamat memori. Anda tidak benar-benar melakukan apa-apa dengan string itu sendiri. Jadi bahkan jika Anda tidak tahu bagaimana Anda akan memecahkan masalah ini dalam kode, tingkat tinggi, secara konseptual, apa yang perlu kita lakukan untuk membuat ta copy sejati s, rupanya? Ya. >> [Mahasiswa] Berikan lokasi baru? >> Tepat. Kita perlu memberikan t lokasi baru. Kita perlu entah bagaimana membuat sebuah dunia di mana kita mendapatkan sepotong baru memori, yang hanya demi kejelasan, aku akan menggambar tepat di bawah satu ini, tapi itu tidak perlu berada di sana. Tapi perlu ukuran yang sama, jadi saya akan menggambar garis-garis vertikal di tempat yang sama. Tidak apa-apa jika ini adalah sampah semua awalnya. Siapa yang tahu apa yang ada di sana? Tetapi langkah 1 akan harus memberi saya memori sebanyak yang saya butuhkan agar sesuai salinan halo, kemudian mencari tahu bagaimana untuk menyalin h di sini, e di sini, l sini dan sebagainya. Tapi ini harus sudah merasa sedikit jelas bahkan jika beberapa detail yang masih abstrak. Untuk menyalin string ini ke dalam ini, itu hanya untuk loop atau loop sementara atau sesuatu dengan yang Anda sudah menjadi semua lebih akrab. Jadi mari kita coba ini. Biarkan aku pergi ke copy2.c. Dalam copy2.c kami memiliki hampir program yang sama kecuali untuk jalur 27. Ini terlihat sedikit rumit, tetapi jika kita jatuhkan itu sepotong demi sepotong, sisi kiri adalah sama. Char * t menciptakan hal ini dalam memori, meskipun dengan tanda tanya karena kita tidak tahu apa yang ada secara default. Di sisi kanan kita sekarang memperkenalkan fungsi malloc, baru, untuk memori mengalokasikan, memberi saya memori, dan itu tampaknya membutuhkan berapa banyak argumen, berapa banyak hal di dalam kurung? Aku mendengar sungut dari 1 dan 2, tapi itu hanya 1. Tidak ada koma, yang berarti hanya ada 1 hal di dalam tanda kurung. Meskipun ada tanda kurung lain, biarkan saya menyorot apa bagian dalam kurung terluar, dan itu ungkapan ini: (Strlen (s) + 1) * sizeof (char). Jadi jika kita benar-benar berpikir ini melalui, ini mengatakan memberi saya panjang s. Mengapa saya, meskipun, menambahkan 1 ke panjang? >> [Respon siswa tidak terdengar] Tepat. Kami membutuhkan ruang untuk orang ini di ekor, karakter keenam yang tidak memiliki arti English tetapi memiliki arti program khusus. Jadi kita perlu + 1 untuk itu karena strlen mengembalikan harapan manusia panjang, Halo atau 5, tidak memberikan karakter null tambahan. Jadi saya secara manual menambahkan dengan + 1. Dan kemudian ini, * ukuran (char), kami belum melihat ini sebelumnya. Ini bukan teknis fungsi. Ini adalah kata kunci khusus yang hanya memberitahu Anda apa ukuran adalah dari beberapa tipe data pada komputer karena pada kenyataannya, sebagian dari kita memiliki 32-bit komputer. Saya memiliki komputer yang cukup tua di rumah, dan hanya menggunakan 32 bit untuk mewakili pointer. Dan jadi jika saya melakukan ukuran tipe data, mungkin 32 bit. Tapi kalau aku menggunakan komputer baru mewah saya, saya bisa mendapatkan kembali nilai 64 bit untuk sesuatu seperti alamat. Jadi dalam hal ini, untuk amannya super, kita tidak akan sesuatu kode keras seperti - baik, apa ukuran char sesuai dengan apa yang kita katakan sejauh ini? Kami sudah cukup banyak mengatakan secara lisan bahwa itu 1 byte, dan itu cukup banyak benar di seluruh papan. Tapi sekali lagi, asumsi cenderung buruk. Mereka mengarah ke perangkat lunak kereta jika orang menggunakan perangkat lunak Anda dengan cara yang tidak anda inginkan. So abstrak mari kita pergi dan ini hanya lebih umum mengatakan Saya mau ini potongan banyak memori dan setiap potongan memori harus setara dengan ukuran karakter, yang sebenarnya sama dengan 1 dalam kasus ini, tapi itu cara yang lebih generik menulis itu. Jadi jika kata tersebut halo, berapa banyak byte yang tampaknya malloc mengalokasikan untuk hello? [Mahasiswa] Enam. Enam >>. Persis seperti banyak seperti yang telah kita tanda tanya di layar. Dan kemudian mengambil menebak sekarang didasarkan pada pemahaman Anda tentang GetString apa malloc mungkin kembali? >> [Mahasiswa] Sebuah alamat. Sebuah alamat apa? Dari potongan pertama dari memori. Kami tidak tahu apa yang ada karena beberapa fungsi lain bisa saja menggunakan memori ini sebelumnya. Tapi malloc, seperti GetString, mengembalikan alamat dari byte pertama dari memori yang telah disisihkan untuk Anda. Namun, apa yang tidak lakukan adalah mengisi kosong ini dengan karakter null backslash karena ternyata Anda dapat menggunakan malloc untuk mengalokasikan apapun: ints, string, array, mengapung, struktur mahasiswa. Anda dapat menggunakan malloc sepenuhnya umum. Ia tidak peduli atau harus tahu apa yang Anda mengalokasikan memori untuk. Jadi akan gegabah untuk malloc untuk menempatkan \ 0 pada akhir setiap potongan memori itu memberi Anda karena ini \ 0 hal hanyalah sebuah konvensi untuk string. Ini tidak digunakan untuk ints, itu tidak digunakan untuk mengapung, itu tidak digunakan untuk siswa. Dan sehingga Gotcha dengan malloc adalah bahwa beban sepenuhnya pada Anda programmer untuk mengingat berapa banyak byte yang Anda dialokasikan dan tidak pernah menggunakan untuk loop atau while loop dan melewati batas dari sepotong memori Anda telah diberikan. Dengan kata lain, segera setelah Anda mengalokasikan memori, Anda tidak dapat meminta sistem operasi, oh, by the way, seberapa besar dari sepotong memori itu? Itu sepenuhnya terserah Anda untuk mengingat jika Anda memerlukan nilai tersebut. Jadi mari kita lihat bagaimana saya melanjutkan untuk menggunakan memori ini. Sejalan 28 dan 29 mengapa aku melakukan ini? Hanya cek Total kewarasan. Hanya dalam kasus sesuatu yang tidak beres, saya meminta beberapa jumlah gila memori atau saya telah begitu banyak hal yang berjalan pada komputer yang ada saja tidak cukup memori, sesuatu seperti itu, saya setidaknya ingin untuk memeriksa null. Pada kenyataannya, kebanyakan komputer akan memberikan ilusi bahwa setiap program dapat menggunakan keseluruhan RAM Anda, tetapi meskipun demikian, jika pengguna jenis dalam beberapa string panjang gila mungkin karena mereka orang jahat dan mereka benar-benar mencoba untuk crash program atau hack ke dalamnya, Anda ingin setidaknya memeriksa nilai kembali dari malloc dan apakah itu sama dengan nol. Dan jika tidak, mari kita berhenti sekarang karena saya tidak tahu apa yang harus dilakukan dalam kasus itu. Bagaimana cara menyalin string? Ada beberapa cara untuk melakukan hal ini. Ada str menyalin fungsi di C, tapi itu super sederhana bagi kita untuk melakukan hal ini dengan cara kuno. Pertama biarkan saya mencari tahu apa yang panjang s. Saya bisa menempatkan ini dalam loop tetapi aku hanya menaruhnya di sini untuk kejelasan. Jadi n sekarang menyimpan panjang string asli, yang tampaknya 5. Kemudian dalam loop untuk saya, saya iterasi dari 0 pada hingga n, dan pada setiap iterasi saya menempatkan s [i] dalam t [i]. Jadi itulah yang saya tersirat dengan 2 jari saya menunjuk pada string sebelum. Karena ini untuk loop iterates seperti ini, saya akan menyalin h ke sini, e ke sini, l ke sini karena ini adalah s, ini t. Dan kemudian terakhir, sejalan 35 mengapa aku melakukan ini? Saya harus memastikan bahwa saya mengakhiri t string. Dan saya melakukannya dengan cara ini menjadi super eksplisit. Tapi mengusulkan, seseorang, jika Anda bisa, dengan cara yang berbeda untuk melakukan hal ini. Saya tidak benar-benar membutuhkan jalur 35. Ada cara lain untuk melakukan hal ini. Ya. >> [Respon siswa terdengar] >> Katakanlah keras. [Mahasiswa] Kurang dari atau sama dengan. >> Tepat. Kami hanya bisa mengatakan kurang dari atau sama dengan n, yang pada umumnya telah buruk karena hampir selalu ketika kita pergi ke suatu hal yang sama dengan kita menghitung kita pergi 1 langkah terlalu jauh. Tapi ingat, berapa banyak byte yang kita alokasikan? Kami dialokasikan strlen dari s, maka 5 + 1 untuk total 6. Jadi dalam hal ini kita bisa melakukan sesuatu seperti ini sehingga kita menyalin bukan hanya halo tetapi juga \ 0 di akhir. Atau, kita bisa menggunakan fungsi yang disebut salinan str, strcpy, tapi itu tidak akan menyenangkan hampir sama banyak. Tapi itu semua hal ini di bawah tenda. Kemudian terakhir, kami melakukan hal yang sama seperti sebelumnya. Saya memanfaatkan t dan kemudian saya mengklaim bahwa aslinya terlihat seperti ini dan salin terlihat seperti itu. Jadi mari kita coba ini sekarang. Biarkan aku pergi di sini. Membuat COPY2. Kami akan memperbesar dan menjalankan COPY2. Aku akan mengetik halo dalam huruf kecil, dan memang saya mendapatkan huruf kecil halo seperti aslinya tapi modal Hello untuk salin. Tapi aku tidak dilakukan dulu. Saya perlu melakukan 1 hal terakhir di sini. 46 dan 47 jelas membebaskan memori, tapi apa yang benar-benar berarti? Apa yang saya lakukan, apakah Anda berpikir, dengan memanggil baris 46 dan baris 47? Apa efek tidak yang memiliki? Ya. [Respon siswa terdengar] >> Tepat. Anda hanya mengatakan sistem operasi, hey, terima kasih untuk memori ini. Sekarang Anda dapat menggunakannya untuk orang lain. Dan di sini adalah contoh sempurna dari nilai sampah. Saya baru saja menggunakan memori ini untuk menuliskan kata halo di 2 tempat, di sini, di sini, di sini, dan di sini. Jadi ini adalah h-e-l-l-o-\ 0. Tapi kemudian saya sebut baris 46 dan baris 47, dan Anda tahu apa yang terjadi di sana dalam hal gambar? Sebenarnya, tunggu, gambar ini merupakan yang lama. Setelah kita membuat copy, orang ini sebenarnya menunjuk di sini, jadi mari kita menghapus angka dan hanya abstrak pergi sebagai panah kami lagi. Apa yang terjadi dalam gambar ini ketika saya menelepon gratis? [Respon siswa terdengar] >> Bahkan tidak. Jika saya sebut gratis di s dan t - jenis pertanyaan jebakan - gambar ini tidak berubah sama sekali karena memanggil s dan memanggil t hanya memberitahu sistem operasi, hey, Anda dapat menggunakan memori ini lagi, tapi itu tidak mengubah ini untuk null atau beberapa karakter khusus, tidak mengubah hal ini, itu tidak mengubah h atau e atau l atau l atau o baik dalam tempat untuk hal lain. Dalam hal gambar, segera setelah Anda panggilan gratis, tidak ada perubahan. Dan di situlah letak asal nilai sampah karena jika saya kemudian dalam program ini meminta sistem operasi untuk memori lebih dengan GetString atau malloc atau sesuatu seperti itu dan sistem operasi mengatakan, yakin, saya memiliki 12 byte memori hanya membebaskan, menggunakan, apa yang Anda akan diserahkan? Kau akan diserahkan sepotong memori yang kita biasanya akan menarik dengan tanda tanya, tapi apa yang mereka tanda tanya? Mereka kebetulan h-e-l-l-o, h-e-l-l-o. Ini adalah nilai-nilai baru kami sampah segera setelah Anda membebaskan memori itu. Ada implikasi dunia nyata di sini juga. Hal ini terjadi berkaitan dengan RAM, tetapi komputer Anda benar-benar melakukan hal yang sama dengan disk. Kita akan membicarakan ini secara khusus dengan sejumlah masalah di masa depan yang berfokus pada forensik. Tapi apa yang sebenarnya terjadi jika Anda memiliki beberapa file keuangan yang sensitif pada desktop Anda atau JPEG samar dan Anda tarik ke tempat sampah Anda, apa yang terjadi ketika Anda tarik ke tempat sampah atau recycle bin? Kau tahu apa yang saya bicarakan. [Tertawa] Apa yang terjadi ketika Anda sudah diseret bukti bahwa ke recycle bin atau sampah? [Respon siswa tidak terdengar] Nah, begitu hati-hati. Apa yang terjadi ketika Anda melakukan itu? Jawaban singkatnya adalah tidak, kan? File samar atau sensitif masih hanya duduk di sana di suatu tempat di hard drive Anda. Sebagian besar dari kita setidaknya telah belajar dengan cara yang keras bahwa Anda perlu untuk mengosongkan sampah Anda atau Anda recycle bin untuk benar-benar menghapus file. Dan memang, ketika Anda mengklik kanan atau klik pada Kontrol sampah Anda dapat atau pilih File, Empty Trash atau apa pun dan Anda benar-benar mengosongkan tempat sampah atau recycle bin, apa yang sebenarnya terjadi kemudian ke gambar ini? Lebih apa-apa. Jadi tidak ada yang benar-benar terjadi pada disk. Dan jika kita hanya sementara ngelantur dan menulis - aku akan hanya menggunakan bagian belakang ini. Jadi sekarang cerita berubah dari RAM, yang mana program tersebut ada saat Anda sedang menjalankan mereka, ke disk, yang mana mereka disimpan jangka panjang bahkan ketika listrik padam, untuk saat ini - dan kami akan kembali ke hotel ini di masa depan - mari kita berpura-pura bahwa ini merupakan bagian dalam hard drive komputer Anda karena kembali pada hari mereka digunakan untuk menjadi disk melingkar, seperti disket. Jadi jika Anda memiliki beberapa file Excel sensitif, mungkin mengambil ini sepotong memori pada disk komputer Anda, dan aku hanya menggambar 1s sewenang-wenang yang sama dan 0s. Ketika Anda men-drag file seperti itu untuk sampah Anda bisa atau recycle bin, harfiah tidak terjadi karena Apple dan Microsoft baru saja memutuskan sampah dan recycle bin benar-benar hanya placeholder sementara. Mungkin akhirnya OS akan kosong untuk Anda, tetapi biasanya, tidak melakukan apa-apa, setidaknya sampai Anda benar-benar rendah pada ruang. Namun, ketika Anda pergi ke tempat sampah kosong atau kosong recycle bin, sama, tidak ada yang terjadi pada gambar ini. Semua yang terjadi di tempat lain di komputer Anda, ada beberapa jenis tabel. Ini semacam seperti contekan kecil yang mengatakan bahwa, katakanlah, resume.doc, sehingga resume Anda dalam file Microsoft Word yang digunakan untuk tinggal di lokasi 123 pada hard disk Anda, tidak ada di memori dan tidak dalam RAM tetapi pada hard disk Anda, dan samar Anda JPEG hidup pada 456, dan Anda file Excel tinggal di 789 atau di mana pun. Ketika Anda menghapus file dengan benar-benar mengosongkan sampah atau recycle bin, gambar ini tidak berubah. 0s dan 1s pada hard drive Anda tidak pergi ke mana pun. Tapi ini tabel, database ini sedikit macam, tidak berubah. Ketika Anda menghapus resume Anda, itu seolah-olah file tersebut dihapus dalam arti tertentu, tetapi semua komputer tidak akan lupa di mana hal yang hidup pada hard drive Anda. The 0s dan 1s yang membentuk resume Anda atau file-file lainnya masih utuh. Jadi jika Anda melakukan ini sengaja, masih ada kemungkinan non-nol bahwa Anda dapat memulihkan data Anda menggunakan Norton Utilities atau beberapa perangkat lunak komersial Tujuan yang dalam hidup adalah untuk menemukan 0s dan 1s yang semacam yatim piatu, dilupakan di sini tapi kiri di sini, sehingga Anda bisa mendapatkan data Anda kembali. Atau peneliti forensik dengan polisi atau FBI akan benar-benar mengambil hard drive dan benar-benar mencari pola 0s dan 1s yang terlihat seperti JPEG, terlihat seperti file Excel, dan memulihkan mereka dengan cara itu bahkan jika komputer telah melupakan mereka di sana. Jadi satu-satunya cara untuk benar-benar menghapus data, seperti yang akan kita bahas di masa depan, adalah untuk menggosok atau menghapus file atau hard disk dengan - Anda tidak bisa benar-benar menyingkirkan 0s dan 1s karena jika tidak Anda akan mulai dengan drive GB hard dan Anda akan berakhir dengan hard drive megabyte jika Anda terus-menerus yang menghapus, harfiah, 0s dan 1s. Jadi apa yang akan Anda lakukan jika Anda benar-benar ingin untuk menutupi trek Anda dan masalah mendasar adalah bahwa masih ada 0s dan 1s pada disk? Saya melihat seseorang isyarat bahwa Anda secara fisik akan menghancurkan perangkat. Itu akan bekerja. [Tertawa] Tapi kalau itu semacam sebuah solusi yang mahal, apa yang akan menjadi lebih masuk akal? Ya. >> [Mahasiswa] Timpa mereka. >> Timpa mereka dengan apa? >> [Mahasiswa] Data lain. Data lain. Anda hanya dapat menimpa disk dengan 0s atau 1s atau semua 0s, semua 1s. Dan itulah memang apa beberapa perangkat lunaknya. Anda dapat membeli perangkat lunak atau bahkan mendapatkan perangkat lunak bebas, dan bahkan dibangun untuk Mac OS hari ini, kurang begitu di Windows, adalah kemampuan untuk aman menghapus. Sebenarnya, jika Anda ingin semua rumah run hari ini jika Anda memiliki Mac dan melakukan hal ini, jika Anda punya beberapa hal di tempat sampah Anda bisa, Anda dapat melakukan Kosongkan Sampah Secure, yang tidak tepat. Alih-alih hanya menghapus file di sini, itu tidak menghapus 0s dan 1s sini, melainkan hanya mengubah mereka semua, misalnya, untuk 0s dan dot, titik, titik. Jadi salah satu dari psets masa depan Anda akan benar-benar sengaja memulihkan data - foto-foto yang kita telah diambil orang, tempat, dan hal-hal di kampus yang kami akan membuat gambar forensik dari kartu memori kamera digital, yang merupakan ide yang sama - dan Anda akan harus ditantang untuk benar-benar menemukan pola yang mewakili JPEG pada hard drive Anda, seperti itu murid yang email saya membaca beberapa minggu yang lalu melakukan untuk memulihkan foto adiknya. Mengapa kita tidak mengambil istirahat 5 menit di sini, dan kami akan berkumpul kembali dengan lebih pada memori. Jadi, di sinilah hal mendapatkan sedikit pikiran-lipatan, tapi ini adalah langkah yang sangat kuat menuju pemahaman ini semua lebih. Berikut ini adalah sebuah program yang disebut pointers.c. Ini adalah salah contoh kode hari ini. Perhatikan bahwa dalam beberapa baris pertama, 19 sampai 22, semua yang kita lakukan adalah sesuatu seperti GetString dan kembali alamat, menyimpannya dalam s. Selanjutnya untuk pset bahkan 3 jika Anda ingin tapi pset 4 dan di mana Anda dapat mulai untuk mengambil roda pelatihan ini dari diri sendiri, tidak ada alasan untuk berpura-pura bahwa string ada lagi. Ini tentu saja hanya mulai mengatakan char *. Sebagai samping, dalam referensi online dan dalam buku-buku Anda mungkin sering melihat bintang di samping variabel. Anda bahkan mungkin melihat ruang di sekitar kedua sisi itu. Semua dari mereka secara fungsional benar. Untuk saat ini, meskipun, kita akan standarisasi pada pendekatan ini untuk membuat super jelas bahwa char * seperti mengatakan pointer karakter. Itu adalah tipe data. Dan kemudian nama variabel adalah dalam kasus ini. Jadi kita sudah string dan kami telah menyebutnya s. Dan kemudian di sini melihat bahwa saya lakukan sebenarnya sedikit tipu daya. Ini disebut aritmatika pointer, yang merupakan semacam super sederhana. Ini hanya berarti menambah dan mengurangi angka untuk pointer. Tapi ini benar-benar bekerja. Program ini tampaknya mencetak 1 karakter string s per baris sehingga hasil akhir - Hanya supaya kita bisa merusak mana hal ini terjadi, membuat pointer, pointer jalankan, biarkan aku tampilannya masuk Sekarang biarkan aku ketik sesuatu seperti HELLO dan jenis Enter dan mencetak 1 karakter per baris. Sampai detik yang lalu, kita akan melakukan ini dengan notasi braket persegi. Kami akan memiliki untuk loop dan kami akan melakukan printf s [i] dan kami akan melakukannya lagi dan lagi dan lagi dengan n backslash di akhir setiap baris. Tapi program ini berbeda. Program ini menggunakan, secara harfiah, aritmatika. Jadi apa yang terjadi di sini? Pertama-tama, sebelum loop ini bahkan mengeksekusi, apa, hanya harus jelas, ini sebenarnya? S? >> [Mahasiswa] Sebuah alamat. >> Sebuah alamat. Dan itu adalah alamat, dalam kasus ini, hello, karakter pertama dalam kata itu, yang h. Jadi s adalah, dalam contoh ini, alamat h. Jadi apa artinya melakukan s + i? Nah, saya mulai pada 0 dalam untuk loop. Kami telah melakukan kali yang banyak. Saya akan pergi ke panjang string, rupanya. Jadi pada iterasi pertama dari loop ini, saya jelas 0. Jadi ungkapan ini mengatakan s + i - lebih tepatnya, s +0--itu jelas hanya s. Jadi apa * s di sini? Sekarang kita menggunakan bintang dalam cara yang sedikit berbeda. Biarkan aku pergi ke depan dan menyingkirkan t karena kita sudah selesai membicarakan t dan salinan s. Sekarang kita hanya ingin menceritakan sebuah kisah yang melibatkan s. Dan sehingga pada saat ini, setelah tipe string, dunia kita terlihat cukup seperti itu sebelumnya dengan hanya s menyimpan alamat h dan lebih umum menunjuk pada string halo. Jika sekarang saya melakukan baris seperti * (s + i), mari kita mencoba ini. Jadi * (s + i). Biarkan aku menyederhanakan ini karena ini adalah 0, jadi ini adalah * (s +0). Nah, tunggu dulu. Sederhanakan lanjut. Ini * (s). Nah, sekarang kurung adalah agak bodoh, jadi sekarang mari kita lakukan * s. Jadi pada iterasi pertama dari loop ini, garis yang disorot, 26, cukup banyak setara dengan mencetak ini. Apa jenis data * s? Dalam konteks ini, karena bintang kebetulan di samping s sendiri, tetapi lebih khusus lagi, karena kita tidak lagi menyatakan s, kita tidak menciptakan variabel lagi, tidak ada menyebutkan char * sejalan 26, tidak ada menyebutkan dari string kata kunci, kita hanya menggunakan variabel yang disebut s, ternyata sekarang bintang memiliki sedikit berbeda dan, diakui, membingungkan makna. * S di sini berarti pergi ke alamat di s dan mencetak apa pun yang ada. Jadi s di sini, * s adalah - semacam Chutes dan tangga, ikuti panah - sini. Jadi ini adalah * s. Jadi apa yang akan dicetak pada iterasi pertama dari loop di jalur 26? Saya mencetak% c, yang merupakan tempat untuk karakter, maka \ n untuk baris baru. * (S + i) di mana i adalah 0 hanya ini. Jadi apa yang Char saya tempatkan di untuk c%? H. Pada iterasi berikutnya dari loop - Anda mungkin bisa melihat mana hal ini terjadi - iterasi berikutnya saya jelas 1, jadi ini berarti s +1, dan kemudian sekarang saya perlu tanda kurung karena sekarang bintang perlu untuk mengatakan pergi ke alamat memori s +1. Apa s? Mari kita memutar kembali waktu dan mengatakan panah ini sekarang tidak benar-benar melakukan kita apapun nikmat. Biar lebih spesifik mengatakan bahwa ini adalah menyimpan nomor 123 karena awal string ini halo, ini adalah alamat 123, ini adalah 124, dan sebagainya. Jadi pada iterasi kedua ketika saya katakan s +1, itu seperti mengatakan 123 +1, atau dikenal sebagai 124, jadi apa arang yang akan dicetak pada iterasi kedua? E di alamat memori 124. Kemudian + lagi, 125, 126, 127, dan loop ini untungnya berhenti sebelum kita sampai di sini karena aku menggunakan strlen untuk memastikan bahwa saya tidak menghitung terlalu tinggi. Jadi itu juga itu. Sekali lagi, ini hanya seolah-olah kita telah melakukan seminggu yang lalu. Biarkan aku menulis di baris bawah meskipun kita tidak ingin melakukan keduanya. Ini identik sekarang untuk ini. Jadi meskipun s adalah string, seperti yang kita sudah menyebutnya selama berminggu-minggu, s benar-benar char *. Jadi jika kita ingin menjadi anal super, itu benar-benar tepat untuk menulis karakter tertentu di lokasi engan menggunakan alamat numerik dan operator ini bintang, tapi terus terang, ini adalah bersih hanya begitu banyak. Jadi ini tidak buruk. Tidak ada alasan untuk berhenti melakukan baris 27 di sini, tapi 26 secara fungsional sama, dan itu fungsional sama untuk persis alasan bahwa kita telah membahas sejauh ini. Dan terakhir, 29 adalah praktik hanya baik. Memanggil bebas dari s berarti bahwa sekarang Anda memberikan kembali memori yang GetString memberi Anda karena lagi-lagi, seperti yang saya sebutkan Senin, GetString selama berminggu-minggu telah memperkenalkan bug dalam kode Anda. Kode Anda selama berminggu-minggu telah memiliki kebocoran memori dimana Anda telah meminta GetString untuk memori, tetapi Anda tidak pernah memberikan kembali. Dan yang sengaja dipilih oleh kami pedagogis karena itu hanya terlalu banyak untuk berpikir tentang awal. Tapi sekarang kita perlu lebih simetri. Jika Anda meminta komputer untuk memori, seperti halnya untuk GetString, seperti halnya tampaknya untuk malloc, Anda sekarang harus untuk pset 4 seterusnya juga gratis setiap memori tersebut. Perhatikan ini berbeda dari mengatakan n int. Anda tidak perlu membebaskan ini karena Anda tidak menelepon GetString dan Anda tidak menelepon malloc. Dan bahkan jika Anda disebut GetInt seperti yang kita akhirnya akan melihat, GetInt tidak mengalokasikan memori untuk Anda karena Anda benar-benar dapat lulus sekitar bilangan bulat dan mengapung dan karakter hanya cara telah kita lakukan selama berminggu-minggu. String, meskipun, yang benar-benar istimewa karena mereka adalah gabungan dari beberapa karakter. Jadi mereka hanya berbeda dari karakter dan mengapung dan ints dan sejenisnya. Tapi kita akan kembali ke yang lama. Setiap pertanyaan kemudian pada awal pointer? Ya. [Pertanyaan siswa tidak terdengar] Ah, pertanyaan yang sangat baik. Salah satu dari beberapa hal C sebenarnya untuk Anda, yang nyaman, apakah angka keluar untuk Anda apa ukuran adalah dari tipe data dan kemudian melakukan semacam perkalian untuk Anda. Hal ini tidak relevan dalam kasus chars karena hampir selalu Char adalah 1 byte, jadi ini hanya bekerja. Namun untuk kepentingan diskusi, jika Anda benar-benar mencetak bilangan bulat dan Anda mencoba untuk mencetak beberapa nilai s yang menunjuk integer, Anda sama tidak perlu melakukan + 4 * saya hanya karena int adalah 4 byte. Aritmatika pointer berarti bahwa C dan compiler melakukan semua yang matematika untuk Anda. Yang harus Anda pedulikan adalah penghitungan dalam semacam rasa manusia. Ya. [Mahasiswa] Jika Anda menyatakan string di dalam untuk loop, apakah Anda harus membebaskan nanti? Pertanyaan bagus. Jika Anda menyatakan di dalam string untuk loop, Anda perlu membebaskan nanti? Anda hanya perlu untuk membebaskan memori yang Anda mengalokasikan dengan GetString atau dengan malloc. Jadi jika Anda hanya mengatakan sesuatu seperti - biarkan aku menempatkan kurung kurawal sekarang jadi semua kode terkait. Jika Anda melakukan sesuatu, meskipun buggily, seperti ini, char * t = s, Anda tidak perlu t gratis karena t tidak melibatkan penyebutan malloc atau GetString. Jika sebaliknya Anda melakukan ini, GetString, maka ya, Anda akan perlu untuk t gratis. Dan pada kenyataannya, satu-satunya kesempatan Anda untuk melakukan yang sekarang dalam lingkaran ini, untuk masalah yang sama dari lingkup yang kita bahas di masa lalu. Jika tidak, Anda akan mengalokasikan memori, mengalokasikan memori, mengalokasikan memori, dan pada akhir program karena Anda berada di luar dari lingkaran itu, t tidak ada, tetapi Anda tidak pernah mengatakan kepada sistem operasi bahwa Anda tidak perlu memori itu lagi. Dan tak lama, untuk pset 4 atau 5 kami akan membekali Anda dengan sebuah program yang disebut Valgrind, yang memiliki semangat yang sama dalam GDB bahwa itu punya sedikit dari sebuah antarmuka misterius, namun tujuannya dalam hidup adalah untuk membantu Anda. Dan Valgrind adalah sebuah program yang akan di masa depan mencari program Anda mencari kebocoran memori, baik dari GetString atau malloc, yang kita akan mulai menggunakan semua lebih karena kita berhenti menggunakan perpustakaan CS50 sebanyak. Kami akhirnya sekarang memiliki semacam kosa kata dan jenis model mental dalam teori yang dapat digunakan untuk memecahkan program ini rusak. Jadi dalam program ini rusak, swap bekerja di dalam swap, tapi tidak pernah benar-benar bekerja di utama karena main disahkan pada x dan y, ingat, dan mereka yang disahkan oleh nilai-nilai, sehingga untuk berbicara. Salinan dari mereka diberikan untuk swap. Pada akhir swap, dan b memang telah dipertukarkan, tapi tentu saja x dan y, seperti yang kita bahas pada hari Senin, belum. Jadi saya mengusulkan hijau di sini bahwa ini sebenarnya solusinya di sini. Dan sebenarnya, biarkan aku menggerakkan bintang saya hanya untuk konsisten meskipun, sekali lagi, secara fungsional ini tidak masalah. Dalam minggu-minggu mendatang kami akan menjelaskan kapan dan mengapa itu penting. Jadi hijau sekarang adalah solusi. Terus terang, terlihat jauh berantakan karena saya memiliki semua bintang. Biarkan saya menunjukkan satu hal. Baris atas sini di mana ia mengatakan int * a dan int b * secara fundamental melakukan hal yang sama seperti biasa. Hal ini menyatakan 2 argumen atau parameter untuk swap, yang pertama adalah sebuah pointer int disebut, yang kedua yang merupakan pointer int disebut b. Satu-satunya hal yang baru pada saat ini adalah kenyataan bahwa ada bintang di sana. Apa artinya? Bukanlah int, b tidak int. A adalah alamat int dan b adalah alamat dari int yang berbeda. Di sini, ini adalah di mana saya akui C mendapat membingungkan. Sekarang kita menggunakan bintang, tetapi memiliki arti yang berbeda dalam konteks ini. Karena kita tidak menyatakan pointer seperti kita di sini, di sini kita dereferencing hal. Jadi secara teknis, bintang dalam konteks baris pertama, kedua, dan ketiga dalam swap adalah operator dereference, yang hanya berarti pergi ke sana. Jadi sama seperti jari saya mengikuti panah ke h, * Cara pergi ke alamat tersebut dan menemukan saya int yang ada. * Berarti b pergi ke alamat dan lulus saya apa yang ada. Jadi mari kita redraw gambar dari Senin sekarang menggunakan setumpuk frame, bagian bawah salah satu yang akan menjadi utama, satu atas yang akan menjadi swap, sehingga dunia kita terlihat, seperti hari Senin, seperti ini. Berikut ini adalah sepotong memori yang utama akan digunakan. Ingat dari hari Senin bahwa program ini hanya memiliki 2 variabel, satu disebut x dan y yang disebut, dan aku telah menempatkan angka 1 dan 2 di sana. Sekarang ketika saya sebut bertukar seperti saya lakukan pada hari Senin, sebelumnya ketika saya menggunakan versi merah dari program ini, yang terlihat seperti ini, Aku punya 2 parameter, a dan b, dan apa yang kita tulis di sini dan di sini? Hanya 1 dan 2, secara harfiah salinan dari x dan y. Hari ini kita mengubah itu. Hari ini bukannya lewat di ints dan b kita akan lulus dalam 2 alamat. Alamat tersebut terjadi menunjuk ke ints, namun alamat tersebut tidak ints sendiri. Mereka adalah alamat. Ini seperti alamat pos sebagai gantinya. Jadi sekarang kita hanya perlu memberi diriku sedikit lebih detail pada layar. Ini adalah memori komputer saya karena sudah seharian. Sekarang kita perlu beberapa skema penomoran sewenang-wenang. Jadi mari kita hanya mengatakan, hanya kebetulan, bahwa ini adalah alamat memori 123, 124. Anggap saja ini adalah 125, ini adalah 126, dan sebagainya, tapi itu benar-benar sewenang-wenang. Kita hanya perlu beberapa skema penomoran dalam ingatanku. Jadi sekarang ketika aku benar-benar lulus dalam x dan y, saya tidak akan lulus dalam x dan y; Aku akan lulus dalam alamat pos, sehingga untuk berbicara, dari x dan y sehingga apa yang akan disimpan di sini dan di sini adalah tidak 1 dan 2, tapi jika Anda dapat melihat teks kecil saya, apa yang akan berlalu di sini dan di sini? [Respon siswa terdengar] >> Tepat. 123 akan dimasukkan di sini dan 124 akan diletakkan di sini. Sekarang, karena saya menggunakan bintang dalam cara baris pertama di sini di atas, program saya hanya tahu bahwa 123 dan 124, meskipun mereka jelas bilangan bulat bahwa setiap manusia bisa melihat, mereka harus ditafsirkan sebagai alamat, alamat numerik. Mereka tidak dalam dan dari diri mereka ints, mereka alamat, dan itu karena saya telah secara eksplisit menempatkan bintang-bintang di sana. Jadi sekarang sejalan saya pertama, kedua, dan ketiga kode aktual apa yang terjadi di sini? Mari kita menarik seluruh gambar. Tmp adalah seperti itu pada hari Senin. Khusus tentang tmp apa-apa. Ini hanya lokal 32 bit variabel, dan dalam bahwa saya ternyata menyimpan nilai * a. Sekarang, jika saya hanya berkata tmp = a, apa yang akan saya taruh di sini? >> [Mahasiswa] 123. 123. Tapi itu bukan apa yang saya lakukan. Saya mengatakan tmp = * a. Berarti bintang pergi ke sana. Jadi di sini adalah, 123. Bagaimana saya pergi ke sana? Berpura-pura seperti ada panah. Nah, itu dia, 1. Jadi apa yang akan disimpan dalam tmp, rupanya? Hanya 1. Jadi dengan kata lain, tmp adalah *, * sarana pergi ke alamat yang saat ini dalam, yang ternyata 123. Oke, di sini kita berada di lokasi 123, saya melihat nomor 1, jadi aku akan menempatkan nomor 1 di sana. Sekarang apa yang harus saya lakukan di baris 2, * a = b *? Yang satu ini sedikit lebih terlibat karena sekarang apa itu? Ini 123. Jadi * adalah di mana? Tepat di mana aku berada sebelumnya. Jadi pergi ke sana. Oke. Sekarang, terakhir, dan akhirnya hal ini akan mulai masuk akal, mudah-mudahan, * B berarti apa yang ada di b? 124. Jadi saya harus pergi ke sana, yang merupakan 2. Jadi apa yang harus saya ditaruh dimana? 2 masuk ke sini karena * b * masuk ke dalam. Jadi saya akan melakukan itu. Dan Anda sudah dapat melihat, mungkin, bahwa kita jauh lebih dekat untuk memecahkan masalah ini, bodoh sederhana dengan benar untuk pertama kalinya karena sekarang kita masih memiliki ingatan apa x itu, kami memiliki 2 eksemplar, diakui, dari y, tapi garis 3 sekarang mengatakan * b. Jadi, inilah b. * B berarti pergi ke sana. Jadi di mana lokasi 124? Ini rupanya di sini. Jadi apa yang saya taruh di sini? Jelas, tmp. Jadi sekarang aku melakukan ini. Jadi saya memiliki 1 dan 2 di sini di sini. Dan sekarang apa tentang semua ini, 123, 124, dan 1? Segera setelah kembali swap, memori ini sebagus hilang karena segera setelah kembali swap, sistem operasi bebas untuk menggunakan memori itu lagi di masa depan. Hanya memori utama di bagian bawah dari tumpukan ini disebut tongkat sekitar. Dan jadi kita akhirnya memiliki versi sekarang bekerja. Biarkan aku pergi ke swap.c, dan perhatikan berikut ini. Pada bagian atas program saya sudah berubah prototipe saya untuk menjadi int * dan int * b. Jadi satu-satunya hal saya berubah untuk pergi dari merah, yang buruk, menjadi hijau, yang baik, adalah saya menambahkan bintang-bintang saat ini. Tapi kemudian di sini di menukar sendiri saya harus menyalin, paste apa yang hanya pada slide. Saya memiliki bintang di sini, bintang di sini - yang cocok prototipe - dan kemudian semua hal ini sekarang memiliki bintang kecuali untuk tmp karena penggunaan variabel sementara, tidak ada yang baru di sana. Aku hanya perlu penyimpanan sementara untuk int. Jadi kita tidak perlu bintang di sana. Kita hanya perlu bintang sehingga kita bisa menyeberang semacam ini batas sewenang-wenang antara 2 frame di memori komputer saya. Tapi satu hal terakhir harus berubah, dan Anda mungkin sudah dilirik. Apa baris lainnya jelas berbeda sekarang? >> [Mahasiswa] & x. Ya, jadi 25 adalah baris terakhir dari kode saya perlu mengubah untuk bekerja. Seminggu yang lalu dan bahkan pada hari Senin 25 jalur tampak seperti ini, swap x dan y, dan ini hanya rusak karena jika Anda mengatakan swap (x, y) Anda memberikan salinan x dan y untuk swap, maka itu melakukan hal tersebut, tapi kau pernah benar-benar berubah x dan y sendiri. Jadi bahkan jika Anda belum pernah melihat karakter ini sebelumnya dengan ampersand dalam kode, hanya mengambil menebak. Apa ampersand melakukan, rupanya? [Mahasiswa] Membawa alamat. Membawa >> alamat. Jadi ampersand yang dikatakan memberi saya alamat dari x. Siapa yang tahu di mana itu? Itu terjadi menjadi 123. Saya tidak peduli. Hanya memberi saya alamat dari x. & Y berarti memberi saya alamat y. Dan pada titik cerita yang sangat konsisten dengan gambar kita menarik beberapa saat yang lalu. Jadi saya akan mengakui pointer, tentu bagi saya ketika saya pertama kali mulai belajar ini, pasti salah satu hal yang paling sulit untuk membungkus pikiran saya sekitar. Tapi menyadari, terutama karena kami terus bermain dengan hal-hal seperti, jika Anda memecahnya tersebut semacam super sederhana dari intelektual menarik masalah hanya bergerak di sekitar angka, jawaban untuk banyak kebingungan dengan pointer benar-benar dapat berasal dari para mekanik yang sangat dasar. Berikut alamat. Pergi ke sana dengan bintang. Atau sebaliknya, inilah ampersand. Mencari tahu apa alamat sebenarnya. Baiklah. Jadi di mana semua memori ini berasal? Kami telah ditarik gambar ini beberapa kali, dan saya tetap menjanjikan kita akan kembali ke sana, tapi di sini adalah representasi dari memori komputer Anda itu sedikit lebih daripada label papan tulis kami di sini adalah. Segmen teks di atas mewakili apa sehubungan dengan program anda? [Respon siswa terdengar] >> Maaf? Katakanlah lagi. [Mahasiswa] Program yang sebenarnya. >> Program yang sebenarnya. Jadi dentang 0s dan 1s yang telah disusun setelah menulis kode C dan kemudian berjalan dan menghasilkan berakhir 0s dan 1s sampai mendapatkan terselip di sana dalam memori karena ketika Anda klik dua kali ikon pada Mac atau PC atau menjalankan perintah seperti mario pada prompt Anda, 0s dan 1s dari disk mendapatkan dimuat ke memori sehingga komputer dapat memanipulasi mereka dan mengeksekusi mereka lebih cepat. Data sehingga diinisialisasi dan data uninitialized, kita tidak akan berbicara banyak tentang mereka, tetapi mereka hanya variabel global. Diinisialisasi berarti variabel global yang Anda berikan nilai ke; uninitialized berarti variabel global yang belum memberikan nilai kepada. Lalu ada variabel lingkungan ini yang saya benar-benar akan melambaikan tangan saya di, tetapi mereka ada dan yang menyimpan hal-hal seperti nama pengguna Anda dan lainnya semacam rincian tingkat yang lebih rendah. Namun potongan juiciest tata letak memori Anda adalah hal ini disebut stack dan heap. Tumpukan lagi, harus jelas, adalah memori yang digunakan setiap kali fungsi dipanggil, setiap kali ada variabel lokal dan setiap kali ada parameter yang lulus sekitar. Semua itu terjadi dalam stack. Tumpukan kami belum dibicarakan, tetapi mengambil menebak yang menggunakan tumpukan. Hanya sepotong memori yang berbeda. Hal ini terjadi untuk ditarik di sini di bagian atas, tapi itu konvensi bergambar sewenang-wenang. Siapa yang tampaknya telah menggunakan memori dari tumpukan selama berminggu-minggu? Secara teknis Anda, tetapi tidak langsung. >> [Mahasiswa] GetString. GetString dan malloc. Jadi, inilah perbedaan mendasar. Anda tahu beberapa minggu terakhir bahwa jika Anda memerlukan memori, hanya mendeklarasikan variabel. Jika Anda membutuhkan banyak memori, mendeklarasikan array yang tepat dalam fungsi Anda. Namun masalah kita terus hadapi adalah jika Anda mendeklarasikan variabel lokal dalam fungsi, segera setelah kembali fungsi, apa yang terjadi pada memori dan variabel tersebut? Hanya semacam itu tidak lagi milikmu, kan? Itu hanya menghilang semacam konseptual. Itu masih ada secara fisik, jelas, tapi itu tidak lagi hak Anda untuk menggunakan. Ini jelas bermasalah jika Anda ingin menulis fungsi dalam kehidupan yang benar-benar mengalokasikan memori dan tidak mengembalikannya segera. Kasus di titik: Tujuan GetString dalam hidup adalah memiliki tidak tahu di muka seberapa besar dari string aku akan mengetik pada keyboard, tapi itu harus dapat mengalokasikan memori untuk menahan David atau halo atau seluruh esai bahwa pengguna mungkin telah diketik masuk Jadi GetString telah menggunakan malloc. Malloc karenanya harus menggunakan tidak stack; sebagai gantinya ia menggunakan hal ini disebut heap. Tidak ada yang berbeda tentang memori. Ini tidak lebih cepat atau lebih lambat atau sesuatu seperti itu. Hanya saja secara fisik di lokasi yang berbeda. Namun aturan adalah bahwa memori yang dialokasikan pada heap tidak akan diambil dari Anda sampai Anda menelepon - mengambil menebak - bebas. Sebaliknya, memori apapun Anda meminta pada stack dengan hanya mendeklarasikan array atau mendeklarasikan variabel seperti yang telah kami lakukan selama berminggu-minggu, yang secara default berakhir pada stack. Dan itu baik 90% dari waktu, tetapi pada kesempatan langka di mana Anda ingin mengalokasikan memori dan tetap sekitar, maka Anda perlu menggunakan fungsi seperti malloc. Atau kita telah menggunakan fungsi seperti GetString, yang pada gilirannya menggunakan malloc. Mari kita lihat di mana hal ini mungkin rusak dan kemudian mengambil mengintip di Binky. Kami akan datang kembali ke di masa depan. Berikut adalah program super sederhana bahwa dalam 2 baris pertama melakukan apa? Dalam bahasa Inggris, apa ini pertama 2 baris kode lakukan dalam main? [Respon siswa tidak terdengar] Hati-hati. Ini tidak memberikan alamat dari x atau y. [Mahasiswa] Memberikan pointer ke ints. >> Baik. Beri aku 2 pointer ke integer. Dengan kata lain, beri aku 2 potongan memori yang aku terus menggambar hari ini, meskipun saya terhapus sekarang, sebagai kotak. Beri aku 2 potongan memori, yang disebut x, yang disebut y - sebelumnya saya memanggil mereka s dan t - dan apa jenis yang sepotong memori? Ini akan menyimpan alamat. Ini dari * tipe int. Jadi alamat int akhirnya akan tinggal di x, alamat int akhirnya akan tinggal di y, tapi awalnya, apa dalam x dan y? Siapa yang tahu? Sampah nilai. Ini tidak ada hubungannya dengan pointer. Jika kita tidak menempatkan sesuatu di sana, siapa tahu apa yang sebenarnya ada? Sekarang, x. Apa yang terjadi di sini? Hal ini legit sekarang karena x adalah pointer. Ini adalah * int. Jadi itu berarti saya bisa dimasukkan ke dalam x alamat beberapa potongan memori. Apa malloc kembali? Sempurna, ia mengembalikan alamat, alamat dari byte pertama dalam sepotong seluruh memori. Berapa banyak byte ini tampaknya mengalokasikan, misalnya, dalam alat? Apa ukuran int? 4. Jika Anda berpikir kembali ke minggu 1, itu tidak super penting untuk selalu ingat bahwa, tetapi dalam kasus ini itu berguna untuk mengetahui, 4 byte. Jadi ini mengalokasikan pada 4 byte tumpukan dan itu kembali alamat yang pertama bagi saya sewenang-wenang. Sekarang, apa yang x lakukan? A * x = 42 melakukan apa? Jika pada titik ini dalam cerita kita memiliki x, yang terlihat seperti ini dengan beberapa nilai sampah, ini sekarang y dengan beberapa nilai sampah, sekarang di baris 3 saya telah dialokasikan 4 byte. Gambar ini pada dasarnya terlihat seperti ini. Atau lebih spesifik, jika ini adalah alamat sewenang-wenang 123, ini adalah apa cerita kita sekarang tampak seperti. * X = 42 sekarang berarti apa? Itu berarti pergi ke 123 alamat dan menempatkan nomor 42 di sana. Saya tidak perlu menggambar garis-garis karena kita tidak melakukan string. Aku seharusnya hanya ditulis seperti ini, dan hanya untuk kepentingan demonstrasi ini, 42 sebagai jenis int memakan banyak ruang, 4 byte. Jadi itulah apa yang terjadi di sana, tapi ada masalah sekarang. * Y = 13. Apa yang akan terjadi di sini? Masalahnya adalah * y di dunia disederhanakan kami hanya berarti pergi ke alamat di y. Apa yang ada di y? Ini adalah beberapa nilai sampah. Jadi mari kita asumsikan bahwa nilai sampah adalah 5551212, sesuatu yang gila seperti itu. * Y cara pergi untuk mengatasi 5.551.212. Itu seperti di sini. Ini tidak ada, misalnya. Jadi * y mendapat 13 berarti saya sedang mencoba untuk menarik 13 di sini. Itu tidak ada. Saya sudah melebihi segmen papan tulis. Apa yang saya dapatkan? Itu segmentasi samar pesan kesalahan karena saya sedang mencoba untuk dimasukkan ke dalam memori nilai seperti 13 di tempat yang tidak ada. Sisa program bisa bekerja baik-baik saja, tapi sampai saat itu tidak. Jadi mari kita coba untuk menceritakan kisah ini. Kami akan kembali ke bahwa sekali kita telah berbicara tentang hex. Mari kita kembali ke ini dan menyimpulkan dengan hal ini disebut Binky, yang recall adalah seorang profesor Stanford duduk di rumah bermain dengan claymation, untuk menceritakan kisah persis bahwa program yang sama. Ini hanya sekitar 3 menit. Disini kita memiliki Binky. [Speaker pria di video] Hey Binky, bangun. Sudah waktunya untuk bersenang-senang pointer. [Binky] Apa itu? Pelajari tentang pointer? Oh, goody! [Speaker laki-laki] Nah, untuk memulai, saya kira kita akan membutuhkan beberapa pointer. [Binky] Oke. Kode ini mengalokasikan 2 pointer yang dapat menunjuk ke bilangan bulat. [Speaker laki-laki] Oke. Nah, saya melihat 2 pointer, tetapi mereka tampaknya tidak akan menunjuk ke apapun. [Binky] Itu benar. Awalnya, pointer tidak menunjukkan apa pun. Hal-hal yang mereka menunjuk disebut pointees, dan pengaturan mereka adalah langkah terpisah. [Speaker laki-laki] Oh, benar, benar. Aku tahu itu. Para pointees terpisah. Eh, jadi bagaimana Anda mengalokasikan sebuah Pointee? [Binky] Oke. Kode ini mengalokasikan Pointee integer baru, dan bagian ini menetapkan x untuk menunjukkan hal itu. [Speaker laki-laki] Hei, yang terlihat lebih baik. Jadi membuatnya melakukan sesuatu. >> [Binky] Oke. Aku akan dereference x pointer untuk menyimpan nomor 42 ke Pointee nya. Untuk trik ini saya akan membutuhkan tongkat sihir saya dereferencing. [Speaker laki-laki] tongkat sihir Anda dari dereferencing? Itu bagus. [Binky] Ini adalah apa yang tampak seperti kode. Aku hanya akan mengatur jumlah dan ... [Bermunculan suara] [Speaker laki-laki] Hei lihat, ada kelanjutannya. Jadi melakukan dereference pada x mengikuti panah untuk mengakses Pointee nya, dalam hal ini untuk menyimpan 42 di sana. Hei, coba gunakan untuk menyimpan angka 13 melalui pointer lain, y. [Binky] Oke. Aku hanya akan pergi ke sini untuk y dan mendapatkan nomor 13 mengatur dan kemudian mengambil tongkat dereferencing dan hanya ... [Berdengung suara] Whoa! [Laki speaker] Oh hey, itu tidak berhasil. Katakanlah, Binky, saya tidak berpikir dereferencing y adalah ide yang baik karena pengaturan Pointee merupakan langkah terpisah dan saya tidak berpikir kita pernah melakukannya. [Binky] Hmm, titik yang baik. [Speaker laki-laki] Ya. Kami dialokasikan y pointer tapi kami tidak pernah mengaturnya untuk menunjuk ke sebuah Pointee. [Binky] Hmm, sangat jeli. [Speaker laki-laki] Hei, Anda mencari baik di sana, Binky. Dapatkah Anda memperbaikinya sehingga poin y ke Pointee yang sama sebagai x? >> [Binky] Tentu. Saya akan menggunakan tongkat sihir saya penempatan penunjuk. [Speaker laki-laki] Apakah itu akan menjadi masalah seperti sebelumnya? [Binky] Tidak, ini tidak menyentuh pointees. Itu hanya berubah satu pointer untuk menunjuk ke hal yang sama seperti yang lain. [Bermunculan suara] [Speaker laki-laki] Oh, saya melihat. Sekarang y poin ke tempat yang sama sebagai x. Jadi tunggu. Sekarang y adalah tetap. Memiliki Pointee a. Jadi Anda dapat mencoba tongkat dereferencing lagi untuk mengirim lebih 13. [Binky] Uh, oke. Ini dia. [Bermunculan suara] [Speaker laki-laki] Hei, lihat itu. Sekarang dereferencing bekerja pada y. Dan karena pointer berbagi bahwa satu Pointee, mereka berdua melihat 13. [Binky] Ya, berbagi. Apapun. Jadi kita akan beralih tempat sekarang? [Speaker laki-laki] Oh lihat, kita kehabisan waktu. >> [Binky] Tapi - [Speaker laki-laki] Hanya ingat 3 aturan pointer. Nomor 1, struktur dasar adalah bahwa Anda memiliki pointer dan menunjuk ke sebuah Pointee. Tetapi pointer dan Pointee terpisah, dan kesalahan umum adalah untuk mengatur pointer tetapi lupa untuk memberikan suatu Pointee. Nomor 2, dereferencing pointer dimulai pada pointer dan mengikuti panah yang selama untuk mengakses Pointee nya. Seperti yang kita semua tahu, ini hanya bekerja jika ada suatu Pointee, yang jenis akan kembali ke aturan nomor 1. Nomor 3, penempatan penunjuk mengambil satu pointer dan mengubahnya untuk menunjuk ke Pointee sama dengan pointer lain. Jadi setelah penugasan, 2 pointer akan menunjuk ke Pointee yang sama. Kadang-kadang itu disebut berbagi. Dan itu semua ada untuk itu benar. Bye-bye sekarang. Ini Binky. Ini adalah CS50. Kita akan melihat Anda minggu depan. [Tepuk tangan] [CS50.TV]