[音樂播放] 戴維·J·馬蘭:好吧。 這是CS50,這 是第四週的結束。 今天的話題之一 是數字取證的, 藝術恢復信息。 事實上,即使 你在中間 現在和平就在三 和突圍,下週, 重點將放在 正是這個領域。 因此,最酷的工作之一,我曾經 不得不回來讀研究生, 當我工作的地方 米德爾塞克斯縣地區檢察官 辦公,做取證工作。 所以基本上,馬薩諸塞州 國家警察,有時, 在案件工作時,會 帶來的東西像硬盤驅動器 和軟盤和 存儲卡等。 他們會交給他們 我和我的導師, 我們的目標是要找到證據, 如果有可能對這些媒體。 現在,你可能已經看到一瞥 這個世界取證的 在媒體,電視和電影。 但這份工作,我曾和 敢說這世界上, 是不是很喜歡,你會看到它。 讓我們來看看有哪些 你可能已經看到了。 [視頻回放] - 確定。 現在,讓我們好好看看你。 [音樂播放] -hold它。 跑了回來。 - 等待一分鐘。 向右走。 -There。 凍結。 - 全屏幕。 - 確定。 凍結。 向上擰得過緊上,你願意嗎? -Vector在上 小伙的後輪。 -zoom在這裡在這一點上。 - 帶有合適的設備中, 圖像可以放大和激化。 - 什麼是什麼? - 它是一個提升計劃。 - 你能清楚了沒有? - 我不知道。 讓我們增強了。 - 增強部分A6。 í增強的細節,還有 - - 我認為有足夠的提升。 它釋放到我的屏幕。 - 我增強了她的眼睛反射。 - 讓我們通過運行這個 視頻增強。 -Edgar,可以加強這方面的? -hang上。 -I've一直在研究這種反映。 -There的人的反思。 - 反射。 -There是男人的臉的反映。 -The反思! -There的一個反映。 -zoom在上鏡。 你可以看到一個反映。 - 你能在這裡提升形象? - 你能提高嗎? - 你能提高嗎? - 可我們加強這方面的? - 你能提高嗎? -hold在第二。 我會加強。 -zoom在門上。 -Times 10。 -zoom。 -Move英寸 - 更多。 -wait,停止。 -stop。 -pause它。 -rotate我們75度 繞垂直,請。 -stop。 回去的一部分 關於門了。 -Got圖像增強器,可以位圖? - 也許我們可以使用普拉迪普·辛格 方法看進窗戶。 -The軟件是最先進的。 -The特徵值是關閉的。 - 隨著權 algorithms--組合 - 他的拍攝照明 算法,以一個新的水平, 我可以用它們來 加強這方面的照片。 -lock上並放大的z軸。 - 增強。 增強。 - 增強。 -freeze和提高。 [完視頻回放] 戴維·J·馬蘭:所以這些都是 所有的話,但他們並不 句子中的正確使用。 而事實上,在未來,任何時候 拜託,你聽到有人說一句話, “提升,”輕笑只是一點點。 因為當你試圖提升, 舉例來說,這是發生了什麼。 因此,這裡是一個美麗的照片。 這是CS50自己Daven。 並假設我們想 聚焦於眨了一下眼睛, 或的反射 壞傢伙,顯然是 由安全攝像機拍攝的。 這是發生了什麼時 你放大圖像上 只有數量有限 與它相關聯的位。 這是你會得到什麼。 事實上,在Daven的眼睛 不過是4,也許6個像素 這構成什麼 在若隱若現的存在。 所以,習題集四將最終有 你探索這個世界上,特別是 由一些性質 我們所說的文件I / O,其中 I / O是只是一種奇特的方式 說的輸入和輸出。 所以到目前為止,所有的相互作用 我們已經與一台電腦 已在很大程度上與 鍵盤和屏幕 但沒有這麼多的硬盤, 或保存文件的超越了那些你 自己寫的。 你的計劃迄今有 未建立和保存, 並更新自己的文件。 那麼,什麼是文件? 嗯,有點像JPEG格式。 這是一個形象,你可能 有或上傳至Facebook, 或者看到在網絡上的任何地方。 事實上,那張照片我們只是 Daven的看到的是JPEG格式。 而有趣 關於類似的JPEG文件 是,它們可以被識別, 典型地,通過比特某些型態。 換句話說,它是什麼, 區分JPEG格式從一個GIF 從一個Word一個PING 從Excel文件中的文件? 好吧,這只是不同 比特模式。 而這些不同的圖案 通常,在這些文件的開始處。 所以,當您的計算機打開一個Word DOC,或當計算機打開一個JPEG, 它的外觀通常是在 第一數位的文件中。 如果它識別出模式, 它說,哦,這是一個形象。 讓我展示給 用戶為圖形。 或者說,哦,這看起來像一個Word文檔。 讓我展示給用戶的一篇文章。 因此,例如,JPEG文件, 事實證明,有 相當複雜 引擎蓋下方。 但在大多數每前三字節 JPEG開始與這三個數字。 這樣字節零個,一個,另外兩個是,在 最每JPEG,255,則該數 216,然後是電話號碼255。 ,你就可以什麼 開始做下週 其實底下戳 文件的引擎蓋像JPEG圖片 而像位圖文件,並查看 什麼是一直存在的,只要 當你使用計算機已經。 但是,什麼是不存在一般 寫的十進制數是這樣的。 計算機科學家不 往往在小數點說話。 他們沒有真正的二進制說話。 通常,當我們想 來表達數字, 我們實際使用十六進制, 您可能還記得 ,比如說,從習題集 一,它挑戰 你想想不同的系統。 當然,我們都是熟悉的 與小數,0至9。 我們談到了二進制。 我們真的沒有 用這麼多在這裡 對了,因為電腦會使用它。 但是,程序員會很 常常,但不總是, 用十六進制,這只是意味著 你有你的字母表16個字母, 相對於兩個或兩個10。 那麼,你如何指望更高 比十六進制9? 你去0,1,2,3,4,5,6,7,8,9, A,B,C,D,E,F,只是約定。 但是,什麼是關鍵的是,每個 這是一個象徵。 有沒有10。 有沒有11本身,因為每 你的數字,就像在小數 而就像在二進制,應該只是 是單個字符,按照約定。 所以這則是我們的字母表 我們所掌握的十六進制數。 那麼什麼是JPEG格式的樣子,如果你 要寫出那些前三 不是字節為十進制但是, 例如,為十六進制? 而為什麼是十六進制,甚至所有有用嗎? 好了,快看一個例子。 所以,如果我寫出來的比特 代表這些小數numbers-- 這可能是一個有點生疏 現在從幾個星期前, 但左1和 合適的人是很容易。 255是最大的數字,我們 可以代表與八位。 這是所有的人。 因此,只有一個是輕度 有趣的是中間的一個。 善良的,如果你做出來的 數學,你會推斷出,事實上, 一個是模式, 零代表216。 所以我們只訂定 現在,這些都是正確的。 但為什麼這很有趣? 好了,一個字節,當然,為8位。 而事實證明,如果你認為 一個字節的四位兩個大塊, 像這樣。 讓我補充一些空間。 所以在後。 我只是添加了一些空白 可視化的緣故這裡。 我們怎麼可能現在代表, 比方說,十六進制位各四, 每個四位組? 因此,例如,在左側 現在,我們有1111的二進制文件。 什麼是十進制的數字, 如果你做出來的數學? 你有那些地方,三三兩兩的地方, 四肢著地的地方,和八分的地方。 聽眾:15。 戴維·J·馬蘭:這是15。 因此,如果我們做的八加4 加二加一,得到15。 所以,我可以寫下15以下 1111,但這裡的整點 是十六進制,十進制沒有。 所以不是寫下15,1-5, 我要編寫十六進制, 而如果你想回來,如果你有 零到f,什麼15將是? 聽眾:F。 戴維·J·馬蘭:那麼原來它的F。 而且你可以工作了這一點說, 還有,如果是10,然後單擊OK,f為15。 所以事實上,我們可以重寫 同一組數字為F F的。 然後,如果我們做數學的一點, 我們推斷,該公司的D。 八是很容易的,因為我們 有一個在八分地方。 然後,我們有一對夫婦更多的F F的。 那麼,人類傾向於做了約定 當他們用十六進制是他們只是 更簡潔地寫這一點, 擺脫大部分的空白。 和剛需超清晰 讀者,這是十六進制, 中簡單的約定 人類是你寫零 x,它是沒有意義的其他 比的視覺識別, 又來了一個十六進制數。 然後,你把兩個數字,F f單位這種情況下,則d a,則F F。 所以長話短說, 十六進制剛剛趨於 是有用的,因為它的每一個 數字,零到F,完美線條 了四個比特的圖案。 所以,如果你有兩個十六進制數字, 零到F,一遍又一遍, ,讓你完美 8位或1字節。 所以這就是為什麼它往往 通常是有用的。 有沒有智慧 內容真的除此之外, 比其實際效用等。 現在JPEG文件不是唯一 文件格式的圖形。 您可能還記得,有 像這樣的文件在世界上, 至少從幾年前。 因此,這實際上是 安裝在Windows XP中 對數以百萬計的世界各地的個人電腦。 這是一個位圖文件,BMP。 和位圖文件,你會看到下一個 本週,只是意味著圓點的圖案, 因為他們是所謂的像素, 一張地圖上的位,真的。 那麼,什麼是有趣的,但是, 這個文件格式,BMP,是 該發動機罩的下面,它 已經不僅僅是三個字節 ,組成它的頭,所以 可以說,最初的幾個叮咬。 實際上,它看起來有點 乍看複雜。 你會看到這個在P組。 和得到的東西 特別是出了現在這個 不那麼重要,因為只是事實 即在每一個位圖的開始 文件以圖形格式, 還有一大堆數字。 現在,微軟, 這種格式的作家, 往往那些打電話 事情不是整數和字符 和花車,但文字和D 單詞和長和字節。 所以,他們只是不同的數據類型。 他們是不同的名字 同樣的事情。 但你會看到,在P設定四。 但是這僅僅是說,如果一個人的 雙擊某些文件.BMP他 或她的硬盤驅動器,並打開一個窗口 一個顯示他或她的形象, 發生因為操作 系統想必注意到,不僅 .BMP文件擴展名 在文件名中, 而且事實上,有一些 公約比特模式 在開始的時候 位圖文件。 但是,讓我們現在專注於 這樣一個複雜的文件, 而是對這樣的事情。 這裡假設gedit中,我 只是開端 的程序,非常簡單。 我有一些包括向上頂。 現在我已經得到了#包括“structs.h”,但 我會回來的,在一個時刻。 但是,該方法適用於現在。 因此,這是一個程序 那將實施 如處長的數據庫。 因此,學生的數據庫, 和每一個學生在世界 有一個名字和一個房子,可能是一些 其他的東西,但我們會保持它的簡單。 每一個學生都有一個名字和一個房子。 所以,如果我想寫一個 計劃,其目的在生活中 剛剛從循環 零上最多三個, 如果有三名學生 在哈佛大學。 我只是想,用GetString的, 每個學生的名字和房子, 然後只是打印出來的那些。 這有點像週 其中,第二週的東西,現在, 在這裡我只想對 環或類似的東西。 我想打電話給GetString的幾 次,然後打印為f的幾十倍。 所以,我怎麼可以這樣做,但是, 當這兩個名字和房子 所涉及的每一個學生? 所以,我的第一反應可能 可以做這樣的事情。 我會先說,好了,給我, 說,叫名字的字符串數組。 我不想硬編碼3在這裡。 我想要什麼就放那裡? 所以學生們,因為這只是 在頂部聲明一個常數, 就這樣我就不必硬編碼 3在多個地方。 這樣一來,我可以改變它一個地方, 它影響的變化隨處可見。 然後,我可能會做 串安置學生。 而現在,我可能會做這樣的事情 為(int i = 0;我<學生,我有用。 所以,我打字快​​,但這是 可能熟悉的語法了。 而現在,這是更近一些。 如果我想要把在第i個 學生的名字,我想我做到這一點。 然後,沒有名字 但房子級別I。 我這樣做,GetString的,並讓 我回去和修復這條線。 同意嗎? 不同意? 這不是很人性化。 我還沒有告訴用戶該怎麼做。 但現在,如果我還 希望以後,我們 比如,打印這些東西 out--所以TODO後。 我會做更多的 this--這無疑就是 正確實施 越來越名字和房子,三 它們的總的每一個,從用戶。 但是,這不是很好的設計,對不對? 如果學生已經不僅僅是一個名字 和一所房子,但也是一個ID號, 和一個電話號碼, 和一個電子郵件地址, 也許一個主頁,並 也許是Twitter的手柄, 和任意數量的其他細節 一個學生或一個人有關, 更普遍。 我們該如何開始添加 功能,這個程序? 嗯,我覺得最簡單的方法可能 可以做這樣的事情,比方說, 詮釋IDS學生。 這樣我就可以把所有的標識在了那裡。 然後,對於一些 如電話號碼, 我不知道如何 代表了,只是還沒有。 因此,讓我們繼續前進,只需要調用 這個Twitter的學生,其中 是有點怪,但 - 和一幫更多的領域。 我已經開始有效 複製並粘貼在這裡。 這是要相當長 笨拙的很快,對不對? 那豈不是很好,如果有 在世界的數據結構稱為 而不是整數或字符串,但一些 較高的水平,一個抽象,所以 可以說,被稱為是學生嗎? Ç沒有配備內置 對學生的功能, 但如果我想給它這樣的? 嗯,事實證明,我要去 打開一個名為structs.h這裡的文件, 你可以準確的做。 我們打算從現在開始這樣做。 和P組三個的引擎蓋下面, 你已經這樣做了。 有沒有這樣的事,作為一個克矩形或 在編程語言C的克橢圓形 人們在斯坦福實現這些 由此處使用這種方法的數據類型, 宣布自己的新數據 使用new關鍵字類型 所謂的結構,另一個 一個叫的typedef。 而事實上,即使語法 看上去從東西有點不同 我們已經看到過,在 原則上,這是超級簡單。 這只是意味著“定義一個類型。” 這將是一個 結構和結構 就像是一個容器 多重的東西。 而這個結構是怎麼回事 有一個名為name的字符串, 和一個字符串名為房子。 而且,我們打電話,只是為了方便, 這整個數據結構的學生。 所以,此刻你到 分號,你現在有 創建您自己的數據 類型稱為學生 現在站在旁邊詮釋, 和float和char和字符串, 和g矩形,和g橢圓形,以及任何數目的 其他的事情人發明的。 那麼什麼是這個有用 現在,如果我回去 為結構0,完成本 實施,這是我寫的 提前在這裡,請注意,所有的 不可避免的雜亂的 即將開始發生,因為我加入 電話號碼和鳥鳴和所有 這些其他的事情 學生的定義, 現在它簡潔地包裹起來 因為只有一個陣列的學生。 而每個學生的現在 擁有它裡面多的東西。 因此,僅僅留下一個問題。 你怎麼看名字搞定, 和房子,和ID, 和任何其他的 裡面的學生? 超級簡單的,也是如此。 新的語法,但一個簡單的想法。 您只需索引數組, 正如我們上週和這一樣。 什麼是明確的 新片語法? 只是,,意為“進去了 結構,並得到現場叫 名,拿到所謂的房子現場, 讓學生稱為該領域。“ 因此,在P設定三,如果你 還在努力的, 和大多數人仍 是,要認識到你 開始使用類似的東西 克rects和g橢圓形 和其他的東西似乎沒有了 來自週零個,一個或兩個, 意識到這是因為斯坦福大學 宣布了一些新的數據類型。 事實上,這也正是我們將 什麼時候,以及在P設定四, 我們先來處理事情 像的圖像,位圖,等等。 所以,這只是一個玩笑話和 心智模式是什麼來。 現在,我一拖再拖 有些今天上午。 我是那種好奇,想看看是什麼 其實微軟壁紙 貌似今天。 而事實證明,一個人在2006年 居然跑到幾乎一樣, 在同一地點,以在現實中拍攝 什麼樣子的,這些天。 本場現在是有點雜草叢生。 因此,圖像的現在來講, 讓我們帶回Daven這裡 屏幕和Nicholas上, 而只是提醒你 如果你想和我們一起吃午飯 本週五,頭我們平常網址 這裡。 那麼,我們曾在週一離開了嗎? 我們推出了這個問題,對不對? 這看似是一個正確的 實現交換的, 因此你要帶兩個整數, 一個叫A,一個叫B, 交換它們,就像勞拉在這裡做 在與牛奶和水的階段, 通過使用臨時 變量或空杯, 這樣我們就可以把B,在和中 b移動,而不做亂七八糟的東西。 我們用一個變量。 這就是所謂的溫度。 但是,什麼是根本 問題在週一這個代碼? 是什麼問題就在這裡? 是啊。 聽眾:它佔用更多的空間。 戴維·J·馬蘭:佔用更多 空間,因為我使用的是可變的, 那沒關係。 這是事實,但我 會說沒關係。 這只是32大位 物聯網方案,所以沒什麼大不了的。 其他的想法? 聽眾:這只是交換 這些變量在本地。 戴維·J·馬蘭:沒錯。 它只能在本地交換的變量。 因為任何時候你調用一個函數 - 當我從安嫩伯格托盤 最後一次,你主要在底部。 只要您撥打一個叫做函數 掉期,掉期沒有得到x和y, 原來的值。 什麼交換的GET,我們什麼要求? 聽眾:複製。 戴維·J·馬蘭:所以他們的副本。 所以它得到一個和兩個,如果 記得上次的例子, 但是一個和兩個副本 被成功交換。 但不幸的是,最終, 這些值仍然是相同的。 因此,我們可以看到這與我們的 新朋友,希望廣發行, 您或轉錄因子和Ca的有 在指導你走向如下。 因此,沒有掉召回看起來like--我們 開拓this--看起來像這樣。 我們初始化X要1,Y兩。 有一堆打印F公司。 但隨後,該按鍵通話 這裡是交換,這 正是我們的代碼 就是剛才看到的。 這是正確的,在第一 一目了然,但在功能上, 這個方案行不通,因為 它不會永久交換x和y。 因此,讓我們看到這個,咋暖 在這裡用GDB中,./noswap。 一堆鋪天蓋地的信息 我會擺脫與控制L現在。 而現在,我要 繼續並運行它。 不幸的是,這 是沒有多大用處的。 它運行的程序這裡面 程序調用GDB,調試器, 但它並沒有讓我閒逛。 所以,我怎麼能真正暫停 執行這個程序裡面? 因此打破。 我可以打破任何 行數,1,10,15。 但我也可以打破象徵 說休息為主。 這就是要設置一個斷點 點,顯然在主線16。 而其中的16行? 讓我們去到的代碼 並上升到noswap。 事實上,第16行是 第一個在程序中。 所以,現在,如果我繼續和類型 運行這個時候,回車,就暫停。 因此,讓我們閒逛。 打印x--為什麼是X為零? 而忽略了美元符號。 這還只是票友 使用的程序的。 為什麼為x為零的時刻? 是啊。 聽眾:它暫停前的權利 線16,而不是實際的線16。 戴維·J·馬蘭:沒錯。 廣發行,在默認情況下,已暫停 只是線16日前執行。 因此它沒有執行,其中 意味著x是一些不知名的價值。 我們很幸運,它的 乾淨的東西像為零。 所以,如果我輸入下一個,現在, 現在執行16。 它等待我去執行17。 讓我繼續前進,打印的X. 這是之一。 讓我繼續前進,印刷年。 我現在應該看到了什麼? 聽眾:[聽不清] 戴維·J·馬蘭:大聲一點。 聽眾:[聽不清] 戴維·J·馬蘭:不太一致。 所以,是的,我們看到一些垃圾值。 現在,y是134514064那裡。 好吧,這只是一些垃圾值。 我的程序使用內存 為不同的目的。 還有其他功能。 別人寫我的電腦裡面。 所以這些位已經被用於 其他的價值觀,我所看到的 是一些殘餘 在先使用該內存。 所以,沒什麼大不了的,因為一旦 我鍵入下一個,然後打印Y, 它的初始化 我想要的價值。 所以,現在,讓我們繼續快一點。 n轉到下一個。 讓我們再做一次。 讓我們再做一次。 但我不想打 在這裡,因為如果我 想看看裡面有什麼事情 掉,有什麼命令? 聽眾:步驟。 戴維·J·馬蘭:步驟。 所以這個步驟我變成了 功能,而不是通過它。 而現在,這是一個有點神秘 說實話,但是這僅僅是 告訴我,我在第33行了。 讓我們再次做到這一點。 打印溫度。 垃圾值,負此時, 但是這仍然只是一個垃圾值。 因此,讓我們做下一個,打印溫度。 它初始化為1,這 是x的值,也叫做。 現在,這裡是我們的a和從X來了嗎? 好吧,注意主,我們 所謂的這些值x和y。 然後,我們通過他們交換如下。 點¯x排在第一位,逗號年。 然後,交換可以稱他們為x和y。 但為清楚起見,這是 稱他們為A和B。 但a和b是現在將要 x和y分別的拷貝。 所以,如果我回去GDB,溫度 現在是一年,現在1。 但是,如果我做一個和現在做的打印 A,A已經搬了過來。 牛奶已經倒入前 橙汁的玻璃,或者反之亦然。 如果我下一次再這樣做了,現在 如果我打印出來作為一個全面的檢查, 一是仍然是兩個,但是B現在之一。 坦率地說,它仍然存在。 我不在乎什麼溫度的。 但只要我現在打字,讓我們說, 繼續回去,現在我在最後 該程序。 不幸的是,x是 還是1和y仍然是2。 那麼,什麼是有GDB的效用? 它沒有幫我解決 該問題本身, 但它希望能幫助我 理解它通過實現 ,是的,我的邏輯是對的,但 我的代碼是不是最終有 產生長遠的影響。 所以這是一個問題,我們 要解決現在今天。 但是,讓我們以這種方式到達那裡。 String是一個謊言。 它也沒有一種數據類型 存在於C.它是 是一個代名詞一些 時間的東西, 我們可以揭示如下。 讓我去進取,不斷開拓 一個名為比0。 而非鍵入此一出來, 我們將開始遍歷代碼 我已經寫了,但 這是只有幾行。 所以這是比較-0。 的第一件事情我做 越來越一行文本。 但是要注意什麼,我 做第一次。 什麼是明確約21行有什麼不同? 其實,等一下。 這是一份2。 這甚至不是正確的程序。 好吧,擾流器警報。 好了,所以從不介意。 這就是答案,未來的問題。 這裡是比較-0,和我 要得到一個文本行。 程序要簡單得多。 因此,這很簡單。 這就好比第一週,第二週的東西 眼下。字符串s = GetString的。 現在,我再說一遍下來這裡。 串T = GetString的。 然後,在該過去的事 程序,正如它的名字所暗示的, 是我要嘗試對它們進行比較。 因此,如果S,第一個字符串, 等於= T,那麼我 要說你輸入同樣的事情。 否則,我會說 你輸入不同的事情。 因此,讓我們編譯並運行這個程序。 所以要比較為零。 看起來不錯。 沒有編譯錯誤。 現在讓我繼續前進 並鍵入./compare-0。 讓我繼續前進,說些什麼 :Daven和東西:羅伯。 與I型不同的東西。 到目前為止,一切都很好。 程序似乎是正確的。 但是,讓我們再次運行它。 說些什麼:加布。 說些什麼:加布。 好吧。 也許我打空格鍵 什麼時髦。 讓我們再做一次。 所以Zamyla。 Zamyla。 不同的東西。 那麼到底是怎麼回事? 因此,我們有以下兩行 代碼的GetString被調用兩次。 然後,我只是 試圖比較s和t。 但真正那麼是怎麼回事? 嗯,我的手寫的要 屠夫這個例子有點。 而且,我們居然丟 這件事在這裡,也是如此。 因此,我們必須像一條線 字符串s = GetString的。 所以,這只是第一 有趣的線從該計劃中。 但是,這段時間一直 正在進行的引擎蓋底下? 以及,在左手側是字符串, 這是某種類型的變量, 而且它稱為S。 所以,我知道,這是使用的內存, 或RAM,在我的電腦不知何故。 所以,我要抽象 繪製一個正方形。 32位的,它的出現,但 更多的是在未來。 然後,這是怎麼回事了嗎? 那麼,很明顯的GetString 從用戶獲取的字符串。 和GetString了 Zamyla或加布或Daven。 因此,讓我們選擇第一 那些的,這是Daven。 所以,有效,什麼的GetString了 我在第一種情況是D-A-V-E-N。 然後,還有什麼做 它給我的秘密? 聽眾:[聽不清] 戴維·J·馬蘭:是啊, 在/ 0或空字符。 因此,有效地給了我一個字符串。 但是,我們已經知道,從以前的 看著一個字符串只是一個數組 字符,它的終止 這個特殊的標記字符,/ 0。 但是,如果這是真 這是一個正方形, 這顯然是一個更大的矩形。 事實上,這是, 我要求中,只有32位。 而這顯然超過32 位,因為這很可能是 八加八加8 加八加八, 只是因為在ASCII碼的字節。 到底如何我們要適應 Daven到這裡這個小盒子? 那麼,什麼是GetString的真正在做什麼? 好了,該網格在這裡代表 我的電腦的內存或RAM。 因此,讓我們武斷地說,如果 每一個都代表一個字節, 那麼,我們能想到的每一個 字節為具有一個地址, 像33牛津街,或34 牛津街,或35牛津街。 所以就像家庭有地址 和建築物有地址, 這樣做的單個字節 記憶有地址或號碼 唯一地識別它們。 現在,這是任意的。 但要保持簡單,我要 用十六進制只是按照慣例, 但0X意味著什麼等 比“,這是十六進制。” 而我要去聲稱, “D”結束於字節的一個存儲器中。 我沒有什麼其他的事情 內存,所以Daven拿到了第一個景點 在字節之一。 那麼,這將是0X2。 這會為0x3。 這將是為0x4。 這是要為0x5。 這將是為0x6。 但是,一旦你開始思考 什麼電腦做的 引擎蓋下方, 你就可以開始來推斷 怎麼啦,幾年前,會 有C本身實現的。 什麼是可能的GetString returning--因為它 感覺這不是 返回Daven,本身 因為他肯定不會 適合在這個小box-- 那麼,什麼是可能的GetString返回? 聽眾:[聽不清] 戴維·J·馬蘭:Daven的位置。 而且它已經這樣做 自從第一週。 什麼GetString的是真的 返回不是字符串,本身。 那是善意的謊言之一。 它返回的地址 串在存儲器中,唯一的地址。 Daven住在33牛津街。 但更簡潔,加文·生活 在為0x1,地址一號。 那麼,被放在這個 小盒子那麼,要清楚, 是字符串的僅僅是地址。 所以這一切的時候,這 已經持續。 但是,這暗示 現在,如果所有S有 是一個數字,它裡面,誰的 阻止你,程序員, 從把任何數目的 任何變量,只是跳 到的內存塊? 事實上,我們可以看到 這是一個威脅下一次。 但現在,這種感覺不足。 如果我說,讓我 字符串,你給我Daven。 但是,你真的不給我Daven。 所有你給我的是Daven的地址。 我怎麼那麼肯定知道 其中Daven開始和ends-- 故事的越來越weird-- 其中Daven的開始和結束, 然後,下一個 字符串在內存中開始? 好吧,如果你遞過 我Daven的開始, 基本上,我怎麼知道 在那裡他的名字到底是? 特別空字符,這 是更重要的,現在 如果下面的字符串 引擎蓋只是確定 通過唯一地在存儲器中的位置。 所以這一切的時候,那是 什麼是怎麼回事。 所以,當我們現在看 這裡的代碼,解釋 如果你會在第26行的錯誤。 為什麼Zamyla和Zamyla有什麼不同? 為什麼加布和加布有什麼不同? 是的,在後面。 聽眾:他們有不同的地址。 戴維·J·馬蘭:很簡單,因為 他們有不同的地址。 當你調用GetString的,因為 再次,我會盡快在這裡, 如果這是第二行,串 T,因為我在該程序中一樣, 等於另一個電話給GetString。 下一次我打電話 GetString的,我要去 以得到不同的塊的內存。 GetString的允許 問工作 系統越來越多的內存。 它不會重複使用相同的 六個字節每一次。 這將得到一個新的 塊的存儲器,其中 裝置噸是會得到 其他一些價值在這裡。 所以,當我做s等於= T,你不比較 ð對這個和A對 這和V反對這一點。 你這個比較 針對這一點,這 坦率地說是相當useful-- useless-- 沒什麼用,因為誰真正 關心那裡的字符串在內存中? 事實上,我們還沒有。 我們不是要 啟動特別關懷。 只是在某種程度上,錯誤可能出現 與安全的威脅可能會出現意志 我們真正開始關心這個。 因此,讓我們解決這個問題。 事實證明,你解​​決它超級簡單。 而且,我們其實之前,我 再次表明,會是什麼 怎麼做,如果在CS50類, 你不得不實施 對兩個字符串進行比較。 你顯然不能僅僅用s等於= T。 但是,僅僅從邏輯上講,如何 你比較這串 不要使用C代碼這個字符串? 是啊。 聽眾:剛才做的 for循環[聽不清] 戴維·J·馬蘭:完美。 聽眾:[聽不清] 戴維·J·馬蘭:是的。 只需使用一個for循環或 while循環或什麼的。 但就應用的基本想法,如果 這是內存或陣列的塊 這就是,遍歷 二者在同一時間。 而只比較字母。 而且你必須是一個 小心一點,因為你 不想一個手指 晃過對方 因為一個字符串 比其他的長。 所以你會想檢查 在年底這個特殊的值,則返回null。 但它確實是,在 最後,就這麼簡單。 坦率地說,我們不需要 重新發明了車輪。 下面是兩個版本。 什麼我要在這裡說的是, 而不是比較s等於= T, 我反而要說,如果字符串 第逗號噸相比等於= 0。 現在,什麼是字符串比較? 事實證明,這是一個函數, 帶有C,其目的在生活中 要比較兩個字符串。 攪拌相比,如果我們讀了 手冊頁或文檔或CS50 參考,它會 簡單的告訴你,攪 比較收益或者負 數或正數或零, 其中零表示他們是平等的。 所以只是猜測。 可能是什麼意思,如果 攪拌收益比較 負值或正值? 聽眾:大於或小於。 戴維·J·馬蘭:是啊, 大於或小於。 所以,如果你想整個排序 在dictionary--一串字符串 因為我們最終會下來road-- 完善的功能,潛在的使用, 因為它要做到這一點 比較字符串給你,並告訴 你做了來自前B,或不 b來之前,按字母順序排列。 我們正是這樣做。 而且請注意,我沒有一個其他 在本實施例中的事情。 什麼改變了更高的 在這個主要的功能? char *的。 而這是其他善意的謊言。 這一切的時候,當你 在寫字符串, 我們一直在偷偷改寫 字符串為char *,這樣實際上鏗鏘 理解你。 換句話說,在CS50.h 當我們最終會看到, 我們做了一個代名詞叫做字符串 這是同樣的事情為char *。 而現在,只有在知道 *,在這種情況下,至少 裝置的地址。 什麼樣的報告? 嗯,事實上,我說的 char *的,而不是int *或浮動* 也就是說char *的是 一個字符的地址。 所以這裡這個小盒子,又名 字符串,是真的char *類型, 這是說只是一個奇特的方式, 在此框中會去的地址。 並且這是什麼地址是指? 顯然,一個char。 但是,我們絕對可以 必須是int *和其他的東西。 但現在,char *的是最真的 直接的和感興趣的。 所以這個問題是要 上升,不過,一次。 假設我打開了這個節目。 讓我們來看看現在我們可以預測 有什麼不對的代碼。 所以這個方案,複製0,我 要繼續前進,並再次呼籲 GetString的並存儲在s的值。 然後,我為什麼這樣做, 只是從過去幾週的提醒? 我們確實說的GetString 有時,則返回null。 是什麼意思,如果 的形式返回空值? 出事了。 這可能意味著該字符串是太 大,計算機的內存不足。 它發生超,超,超 很少,但它可能發生。 我們要檢查它, 這就是我們所做的。 因為我們現在看到的,如果你不這樣做 開始檢查習慣性的東西 像空,你可能 真正開始去 到存儲器中的地址是無效的。 而你要開始誘導 越來越多的細分故障。 或者在Mac還是PC,只要 使計算機掛起 或程序凍結,有可能。 所以,現在,我要求在複製0.c,我 現在要通過的方式來複製這些字符串 線28。 然後,我會 如權利要求在底部 在這裡,我要 改變其中之一。 所以注意到這一點。 我打電話是我們的老朋友strlen的。 而在英語只是解釋 這行34是幹什麼的? 什麼噸支架0 表示在左邊。 是啊。 聽眾:T的第一個字符? 戴維·J·馬蘭:T的第一個字符。 就是這樣。 噸的第一個字母,我想 指定的大寫版本 在噸的第一個字符。 因此,這是資本 第一個字母。 然後,在最後一件事,我做的 在這個計劃是我要求這裡的 原來,S,和這裡的副本,T。 但根據故事我們只是 說什麼串真的是, 什麼是28行真的 做的,什麼是 所產生的錯誤會 要在屏幕上? 因此,首先,第一個問題,28。 什麼是串T = S真的在做什麼? 如果我們有在左手 這裡邊串T = S; 這給了我一個盒子 在這裡,一個盒子在這裡。 並假設該地址是0X, 比方說,50這時候,隨意。 什麼串T = S 做引擎蓋底下? 聽眾:[聽不清] 戴維·J·馬蘭:它存儲在內存中 有地址,所以為0x50去那裡。 所以,如果現在我去的第一個 字符T和大寫的, 我是什麼切實做送? 我真的做同樣的事情,對不對? 因為如果地址0x50--,只是,我 沒有太多空間在黑板上這裡, 但假設這是0X50到這裡, 某處在我的電腦的內存中。 而我,比如,加布 在這裡小寫,這樣。 我已經說過噸支架 0被資本化。 嗯,T支架0 T中的第一個字母。 所以,小克將要 成為大灣但是問題 是,是什麼而是也指向? 聽眾:相同。 戴維·J·馬蘭:同樣的事情。 因此,一個簡單的解釋或許是, 即使語法是有點怪異。 因此,讓我們做到這一點。 使複製的0,然後./copy-0。 說些什麼:加布。 不幸的是,這兩個 他們現在已經被資本化, 但對於基本 原因是我們根本 現在要處理的地址。 那麼,我們如何開始 address--沒有雙關語intended-- 我們該如何著手解決 這方面的問題? 那麼,在copy1.c,事情進展 變得有點複雜。 但我會要求 概念上很簡單的解決方案。 所以很難得到乍一看。 不是一件容易的事為先 一次打出來,也許, 但是,如果該問題是 簡單地做T =的只有我 複製地址什麼的, 再次,如果我可以選擇你, 將是解決方案 在實際拷貝的字符串? 聽眾:我們可能會 再次使用一個循環。 戴維·J·馬蘭:是的。 所以,我們要再次需要一個循環。 而且,因為如果我們想複製 一個字符串s轉換另一個字符串, 我們可能想這樣做 逐字符。 但問題是,如果 這本來是S, 現在我們需要明確啟動 在t分配內存。 換句話說,讓我們 重繪這是最後一次。 如果是字符串s = GetString的。 讓我們把這個在這裡,也是如此。 這是GetString的。 然後,畫面的東西 像將是象以前那樣 G-A-B-E-/ 0。 這看起來有點像這樣。 和S因此,我們稱這種為0x50, 那將是51,52。 因此,這是為0x50。 然後,我做的串T。 在內存方面,這只是將 給我這樣一個小廣場。 那麼什麼是關鍵的一步呢? 如果我想複製s轉換T,什麼 空白,我們需要在這裡填寫? 或者是什麼,我們需要 做在一個較高的水平? 是嗎? 有人在嗎? 是啊。 聽眾:我們需要[聽不清]。 戴維·J·馬蘭:是的,我們 需要填寫這個空白。 我不能複製,然後 利用Gabe的名字 直到我問操作系統 對於內存另一塊 這至少一樣大的原稿。 所以這給我們留下了一個問題。 我如何向操作系統不 只是一個簡單的小pointer-- 因為這是所謂的,一個 地址,pointer--不 一個簡單的小盒子 像這樣所謂的一個字符串? 我怎麼問工作 系統內存一大塊? 到目前為止,我只得到了回 間接調用GetString的。 因此,如何的GetString 即使得到它的內存? 嗯,事實證明,有 這個其他的功能在這裡 那我們現在就開始使用。 現在,這種方式看起來更神秘than-- 我是誰可以看到它 - 唯一一個 這條線看上去方式更隱蔽 那麼就應該第一眼。 但是,讓我們逗它拆開。 在左邊,我的char *噸。 因此,在英語,讓我們開始制定 正確的句子中的技術術語。 因此,這是分配 char類型的變量*稱為T。 現在,這究竟意味著什麼? 那麼,這意味著,我該怎麼 把這個變量稱為T? 一個字符的地址。 所以,這僅僅是簡單的, 更合理的方式 的說明的左手側。 因此,創建這個盒子在這裡只。 這樣的右手側, 據推測,是怎麼回事 分配的大 內存塊是如何? 因此,讓我們取笑這個分開。 它壓倒性的第一眼, 但是這是怎麼回事裡面嗎? 首先,有malloc的,這 顯然是我們的新朋友, “內存分配”。 因此,這是傳遞的參數 進去,所以這是一個相當大的爭論。 因此,讓我們取笑這個分開。 當然,第strlen的,代表the-- 聽眾:字符數。 戴維·J·馬蘭:就在 s中的字符數。 所以s的長度,原來的字符串。 因此,G-A-B-E。 因此,它可能是在這裡為四個。 之後我為什麼要做1 調用第strlen的? 聽眾:[聽不清] 戴維·J·馬蘭:對於 特殊的空字符。 如果你問我什麼是長度 Gabe的名字,我會說,四名。 在系統底層,不過,我需要 在第五個字節的空字符。 所以這就是為什麼我做了1。 現在,以防萬一你運行這個 程序的計算機比其他的,說, 在CS50家電, 其中一個字符的大小 可能是不同 從我自己的computer-- 事實證明,我可以把這個 運營商的sizeof,只是問了電腦, 什麼是a的大小 char的這台電腦上? 並通過在此乘以5 例如,通過一個字符的大小,這 在大多數計算機上會 僅僅是一個,malloc的 是要分配給我這個大 內存塊在這裡就對了。 而這將return-- 它是一個函數 - 所以它的 要回到我身邊嗎? 聽眾:地址? 戴維·J·馬蘭:什麼樣的報告? 聽眾:內存是分配呢? 戴維·J·馬蘭:的 它的內存分配。 所以,我不知道,坦白地說, 這是怎麼回事結束了。 我要建議 這將結束在均為0x88。 完全是任意的,但 什麼地方比其他的0x50, 因為操作系統,什麼 Windows和Mac OS為我做的,是 請確保它給 我的內存不同的塊。 因此,這是價值所在今 內存塊可能最終。 原來這就是在這裡,均為0x88結束。 所以,現在清楚了,我能理解 這是不一樣的,因為這, 因為他們指著 不同組塊的存儲器。 所以,如果我現在真的想複製此 在,讓我們做你的建議的解決方案。 讓我們只是去創建一個for循環, 和做T支架í得到Š支架島 因為現在我可以使用 這陣般的符號, 因為即使非常的malloc 一般我分配內存, 內存只是連續的字節。 字節,字節,字節,回背靠背。 我可以肯定,作為一個程序員 把它當作一個數組,其中 意味著我可以用這個終於熟悉 符號只是一些方括號。 因此,讓我停在那裡,因為 這是很多一次性全部,甚至 雖然基本思路重溫 是字符串,這一切的時候, 是不是一個新的數據類型本身。 這只是一個所謂的指針, 一個字符的地址, 這只是意味著它是一個數字 由人約定 我們傾向於寫為0X的東西。 但是,這只是一個數字, 像33牛津街, 這恰好是 政務司司長建築物的地址。 對這些細節有問題嗎? 是嗎? 聽眾:我們為什麼檢查 在t等於null? 戴維·J·馬蘭:為什麼我們 檢查噸等於null? 如果我們讀了documentation-- 對malloc的偉大question--, 它會在印刷精美的說, 有時候可能的malloc返回null, 就像GetString的。 事實上,形式返回空值 如果反過來,malloc的返回null, 因為GetString的使用的malloc。 和可能,如果操作系統發生, 的Mac OS,Windows中,無論是簡單的 出內存給你。 所以,這就是發生在那裡。 並且讓我發現一件事 這可能只是打擊你的心 或者完全是太遠了就行了。 不過,讓我拉起來 同樣的for循環複製, 其中,剛才被召回 這個。噸級別I得到Š支架島 尼斯和用戶友好。 再次感覺就像第二週。 但這個版本其實是可以 寫成這樣,看起來神秘。 這是一個技術,稱為指針 算術,地址運算。 但是為什麼這工作? 現在煩人的 的C筆者決定使用 *符號為不同的目的。 我們已經看到了使用一次已, char *的,意思是“給我一個變量 那將包含 一個字符的地址。“ 在這方面如此的char * 意思是“給我一個變數。” 不幸的是,如果您使用不帶* 在它前面的單詞,如焦炭, 它現在被稱為 引用操作。 我們會看到更多這樣用不了多久。 但它只是意味著“去那裡。” 這就像說,如果有人遞給我 在一張紙“33牛津街” 如果我做“* 33牛津街,”這意味著 “走在路上到CS的建設。” 因此,*的意思只是去那裡,如果 還有就是在它前面沒有字。 那麼,什麼是T,要清楚? t是該塊的地址 這是還給我的記憶。 s是什麼,要明確的地址, 在這個例子中,我們一直在討論, 小寫加布? s是地址of-- 聽眾:字符串。 作者加布的原名:戴維·馬蘭。 所以它的地址 這個塊的存儲器。 所以,如果我說T +我 - 我的通知, 只是我們的老朋友了。 這只是一個索引變量 這是從零上了迭代 到的字符串s的長度。 因此,這將是零,再一個, 然後二,然後三天,4。 因此,讓我們組裝這些新 從無到有,就像拼圖遊戲一樣,如果你​​願意, 即使再次,語法 遠比划痕更晦澀難懂。 因此,t是一個地址+ i的要給我 數,因為這些都是 我們已經制訂為十六進制數。 但他們只是數字。 因此,如果T的地址,我們說 為均為0x88,什麼均為0x88加零。 即使你不舒服 用十六進制然而,以此來猜測。 聽眾:原來。 戴維·J·馬蘭:仍然均為0x88。 那麼,是什麼*均為0x88是什麼意思? 這意味著,“去那裡”,這意味著 有效,“把你的手指在這裡。” 和現在的右手側 該表達式中,*,然後在括號, S + i表示s,這是 這裡的小克解決了。 S + 0,當然,S,不管s是。 所以,現在,它的* s,這就像* 33 牛津街是指去的地址 第 因此,這裡的這個手指,右手。 那我要複製到什麼? 在右側的​​事情,這是 加布,在這裡,小克,到這裡。 那等的影響 在循環的第一次迭代中, 如你提出,儘管它看起來 瘋狂的比什麼都更複雜 我們已經看到過,只是說 到這裡,並在這裡複製該字符。 它給你一張地圖兩個位置。 我們將看到更為了這一點。 但現在,希望僅僅是 介紹其中的一些基本思路。 事實上,讓我們來看看 最後一個節目在這裡, 然後承諾的粘土動畫, 這將使得一切都還好嗎。 好吧。 因此,讓我開up--我們走吧。 因此,讓我 - 我們會回來的 到不久這張圖片。 讓我開了這個最後的例子在這裡。 因此,這裡是一個超級,超級 程序完成 沒有在生活中,做了以下幾點。 它首先聲明兩個變量,X 和y即不是數字此時, 本身。 他們不是整數,本身。 他們顯然是int *。 所以只要任何人,這是什麼意思 如果你的數據類型,你的變量, 是的類型是int *星? 這是一個int的地址。 所以,我不知道它在哪兒呢。 它只是意味著“最終, 這裡的int的地址。“ 為0x50,均為0x88,無論它是在 存儲器中,地址是要在那裡。 而這正是y是 將要,以及。 如果我現在說,X =的malloc(sizeof運算(INT)), 這是說,一個奇特的方式, 哎操作系統通過malloc, 給我足夠的內存的大小 一個int,這可能是 將是32位或4個字節。 那麼,是什麼的malloc返回? malloc的返回地址。 那麼,什麼會得到存放在X? 的組塊的地址 存儲器,四個字節,該malloc的 剛發現我問 操作系統。 現在同時在線 4在此,* X = 42。 只是要清楚, 這是怎麼回事那裡? 在左手側,* X。 這就像* 33牛津街。 因此,* X意味著什麼? 聽眾:去。 戴維·J·馬蘭:進入該地址。 無論那一塊 記憶,去它。 放什麼在那裡,很明顯? 聽眾:42。 戴維·J·馬蘭:42。 好吧,* Y,同樣的想法。 轉到Y中的地址。 把13號在那裡, 但為y的時刻? 聽眾:有沒有記憶的年。 戴維·J·馬蘭:有 對Y沒有記憶。 那麼什麼是ÿ可能 包含,因為我們一直在說什麼? 聽眾:垃圾。 戴維·J·馬蘭:一些垃圾值。 現在,垃圾的價值仍然是一個數字。 它仍然可以被誤認為是一個地址。 就好像一個人 潦草的東西了, 我誤解了它的意思 一些建築在街上。 如果你只是試圖進入 一些建築物不屬於您, 或一些內存塊,你有沒有 已經給出不好的事情可能會發生。 計算機可能會崩潰,或者一些其他的 未確定的行為可能會發生。 所以,前奏的話,要賓基是這樣的。 我還記得,20 一些多年後, 我在那裡的時候,我終於 理解指針。 這就是說,如果 離開這裡在三分鐘 而以為我不 理解指針,實現 我記得20 年,一些瘋狂的原因 何時以及為什麼它最後沉沒 中,坐在我的教學 老鄉,尼沙特梅塔在 艾略特食堂回來。 現在,我想起了 這是因為,這是 的主題時,我在一個 特別是,掙扎。 然後,它最後點擊, 像我敢說很多話題 最終會的。 而現在,以使該感到所有的 更快樂,更讓人信服, 讓我們在最後我們看一下 最後三分鐘,在這裡賓基, 從我們的朋友,尼克 Parlante來自斯坦福大學。 [視頻回放] 嘿,賓基。 醒來! 現在是時候為指針樂趣。 - 什麼是什麼? 了解指針? 噢,好極了! - 嗯,上手的,我想我們 將需要幾個三分球。 - 確定。 此代碼分配兩個三分球, 它可以指向整數。 - 確定。 嗯,我看到兩個三分球,但他們 似乎並沒有被指向任何東西。 - 這就是正確的。 最初,指針 不指向任何東西。 他們指出,被稱為東西 指針對象,並設置他們的 一個單獨的步驟。 哦,對,對。 我知道這一點。 該指針對象是分開的。 呃,那麼你如何分配指針對象? - 確定。 那麼,這個代碼分配 一個新的整數指針對象, 而這部分設置x指向它。 嘿,這看起來更好。 因此,利用它做些什麼。 - 確定。 我將間接引用指針x可 數字42存入及其指針。 對於這一招,我需要我的 提領的魔術棒。 解引用的 - 你的魔術棒? That--這是偉大的。 - 這是什麼樣的代碼如下所示。 我會剛剛成立的號碼,[流行] 嘿,快看。 就這樣吧。 -so做一個提領在X如下 箭頭訪問及其指針。 在這種情況下,存儲器42在那裡。 嘿嘗試使用它來存儲數 13穿過另一個指針,Y。 - 確定。 我就投奔這裡Y, 並獲得了13號成立。 然後,採取的魔杖 非關聯化和公正[叮咚] - 哦! 哦,嘿嘿! 沒有工作。 說,賓基,我不認為提領 y是一個好主意,因為你知道, 建立指針對象 是一個獨立的步驟。 而且我不認為我們曾經做到了。 - 良好的點。 是啊。 我們分配的指針,Y,但我們 從來沒有把它設置為指向一個指針對象。 - 非常細心。 嘿,你看起來好有,賓基。 你可以解決它,從而y點 到相同的指針對象為x? -sure。 我會用我的魔杖 的指針賦值。 -is那將是 像以前一樣的問題嗎? - 沒有。 這不碰指針對象。 它只是改變了自己的指針 指向同樣的事情又。 哦,我明白了。 現在Ÿ指向同一個地方為x。 所以等待。 現在,Y是固定的。 它有一個指針對象。 所以,你可以嘗試的魔杖 提領一次送13以上。 -Uh,確定。 在這裡不言而喻。 [流行] 嘿,看看這個。 現在提領Y上的作品。 而由於指針分享 一個指針對象,他們都看到了13。 是啊。 共享,等等。 那麼,我們現在要切換的地方? 哦,你看。 我們沒時間了。 -But-- - 只是記住三個指針的規則。 第一,基本結構 是你有一個指針, 它指出了一個指針對象。 但指針和 指針對象是分開的, 和常見的錯誤 是要建立一個指針, 但忘了給它一個指針對象。 第二,指針廢棄 開始於指針 並沿用其在箭頭 訪問及其指針。 大家都知道,這 只有當有 指針對象,哪一種 變回規則一。 第三,指針 任務需要一個指針 並將其更改為指向 同樣的指針對象作為另一個指針。 因此,在轉讓之後, 這兩個指針 將指向同一個指針對象。 有時候,這就是所謂的共享。 而這一切就是這麼簡單,真的。 再見了。 [完視頻回放] 戴維·J·馬蘭:這就是它的CS50。 我們會看到你下週。