[Muziek] DAVID J. Malan: Oke dit is CS50 en dit is het begin van week vijf. Dus vandaag, onder uw zitkussens, je zult niets vinden. Maar bovenal, moet u deze, een weinig blijk van onze waardering voor al het werk dat je in het spel van Fifteen. Verwijder gewoon de kleine cirkel op de bodem om te beginnen met het spelen voor de rest van de klas. Zo herinneren dat, of weten dat ingesteld probleem vier, die dit weekend ging uit, gaat het schrijven van een ander spel. Maar deze keer gaat met behulp van een werkelijke grafische gebruikersinterface, geen tekstuele interface zoals Partijtje Vijftien was. En het spel dat voor je ligt, als je nog niet hebt gezien deze volgende, ziet er een beetje zoiets als dit. Ik ga om te gaan in mijn terminal raam hier in GDB. En ik ga om verder te gaan en uit te voeren de personeel oplossing, die u kunt openen nadat u update 50 zoals gewoonlijk. Maar ik ga het in een kleine geheime modus, een beetje paasei, zogenaamde God mode, door zetten van God in argv1. En ik moet mijn eigen weg te volgen, draait het in mijn eigen probleem set directory. Dus nu een volledige versie zie je van het spel van Breakout. In feite is dit losse handen mode. Dus het is eigenlijk - wowed al zou je wel - vrij triviaal om God-modus te implementeren in Breakout, in tegenstelling tot Spel van Fifteen, die sommigen van jullie misschien hebben aangepakt voor de hacker editie. In Breakout volstaat in God modus om gewoon te doen wat, intuïtief met de peddel? Gewoon het gelijk aan wat de horizontale positie is van de bal. En zolang je dit doet in lockstep de bal beweegt dit spel zal nooit, nooit, nooit missen de bal en je zult elke keer winnen. Maar in deze week hacker editie er is meer dan alleen God mode. Er is een aantal andere functies. Onder hen, lasers. Zodat als je echt ongeduldig u kan beginnen neer te schieten de stenen en een paar anderen. En voor degenen onder u die wilt kalibreren standaard versus hacker editie, kan ik zien dat van deze week hacker editie opzet is een weinig meer uitvoerbaar, zeggen, dan God mode was met Game van Vijftien. Dus als u op zoek bent naar een rek en u op zoek bent naar wat extra fun functies doen duik in als interessant. Nu meer praktisch, wil ik erop wijzen op een ding ook. GDB, dat sommigen van jullie misschien nog niet hebben aangeraakt persoonlijk, dat is prima. Maar nu is echt de tijd om te wennen om deze en comfortabel met deze tool omdat het je leven zal maken veel gemakkelijker, echt. Per lezing Rob's op GDB een paar van weken geleden, herinneren dat GDB is een debugger. Het is een tool waarmee je loopt uw programma, maar voer het stap voor stap, lijn door lijn, zodat u rond kunt snuffelen, zodat je ziet dingen gebeuren, dus die u kunt uitprinten waarden van variabelen. Kortom, het geeft je zoveel meer macht dan printDef doet. Nu toegegeven, de interface is vrij mysterieus. Zwart en wit tekstuele interface- voor het grootste deel. De commando's zijn enigszins taai te onthouden op het eerste. Maar ook al zou je de helft nemen een uur, een uur, om dat vooraf te zetten investering van tijd in het, geloof me. Zeker tegen het einde semester het bespaart u een orde van grootte meer tijd dan dat. Zo vroeg in de week duik inch En in termen van Breakout, weet dat je kunt dit doen zolang je hebt de distributie-code of uw eigen code aan de gang in je Pst4 directory. Weet dat je gdb kan draaien. / Breakout. Dit gaat openstellen een venster als dit. Laat ik geef mezelf meer van een terminal-venster. En dan wat ik ga om verder te gaan en te doen, het is niet alleen maar voer het uit. Ik ga eerst een breekpunt te stellen terugroepen, die u toestaat om te pauzeren uitvoering op een bepaalde plaats. Gewoon om dingen eenvoudig ik ga houden te breken op lijn een gewoon door te typen de nummer een. Laat me eigenlijk heropenen dit venster want het wordt een beetje klein zijn. Dus wat ik nu ga doen hier is als ik open mijn raam terminal. Kom op, daar gaan we. Dus nu als ik terug naar dropbox, Pst4 en uitvoeren gdb. / breakout voeren, merken Ik ga om te breken een in te stellen een breekpunt op lijn een. En nu ga ik om te gaan gang en het type uit te voeren. En als ik dat doe, merk niets lijkt te gebeuren. Er is geen pop-up. Er is geen grafische gebruikersinterface nog. Maar dat is begrijpelijk, want ik ben letterlijk op regel een in mijn programma. En merk dat ik snel heb doorgestuurd, specifiek nu naar 62, omdat alle het spul aan de bovenkant van dit bestand is dingen als commentaar en constanten en oninteressante dingen voor nu. Dus nu ben ik de binnenkant van de belangrijkste, het schijnt, op lijn 62. En dit is slechts de verdeling code, terugroepen. Als ik dit openen door te gaan, op dezelfde wijze, in mijn dropbox map in Pst4, in breakout.c. En als ik scroll naar beneden en beneden en naar beneden, en laat mij ga je gang en zet mijn lijn nummers. Wat ik zal zien, als ik scroll naar beneden naar lijn 62, is precies de lijn die we hebben onderbroken op. Dus deze lijn hier, 62, is waar we staan ​​op het punt te zijn. Dus nu in GDB, of ik ga je gang en typ nu naast, voer het gaat voeren die lijn. En voila, we hebben de zogenaamde g venster. Als u niet weet wat een GWindow is, geen zorgen te maken. De spec zal u kennismaken met het, zoals evenals een aantal walkthrough video's ingebed in het spec. Maar nu laten we maken dit tot een iets interessanter. Laat me dit venster bewegen over aan de zijkant een beetje. Laat ik het raam maken een beetje groter dus ik kan meer zien. En nu laat ik ga je gang en opnieuw doen volgende. En daar zijn mijn bakstenen. Als ik typ volgende weer Nu zie ik de bal. En als ik typ volgende weer nu zie ik de peddel. En gelukkig is dit gedit is niet echt samen door het tonen van me alles wat ik wil. Maar nu als ik volgende keer doen, volgende nogmaals, ik ben gewoon verklaren wat variabelen. En ik kan iemand afdrukken van deze jongens uit. Print bakstenen, prenten leven. En nu als ik blijven doen volgende, merken dat ik kom binnenkant van die lus. Maar de code gaat voeren precies zoals ik verwacht. Dus toen ik deze functie geraakt, wacht voor Click, het gaat doen het letterlijk dat. Dus ik leek controle te hebben verloren op het programma. GDB is niet te geven me een andere prompt. Maar niet getreurd. Ga naar mijn spel, klik ergens. En voila, nu overgaat tot lijn 86. Dus nogmaals, het is van onschatbare waarde, uiteindelijk, voor debugging problemen. Want je kunt letterlijk stap voor stap door uw code, print dingen uit en veel, veel, meer. Maar voor nu, deze tools alleen moet krijg je vrij ver. Dus we zijn, natuurlijk, het nemen van een kijkje bij Graphics nu, ineens. En nu onze wereld wordt een beetje interessanter. En weet je, misschien, van enkele van de video's online dat we deze korte broek die je hebt in de gaten als onderdeel van het probleem sets. En ze zijn neergeschoten, doelbewust, tegen een witte achtergrond. En sommigen van hen hebben het onderwijs Fellows tekenen wat tekst op het scherm dat wordt bedekt aan de zijkant ervan. Maar natuurlijk, dit is niet zo interessant in de echte wereld. Dit is slechts een collegezaal met een grote witte scherm en een achtergrond. En onze geweldige productieteam sorteren van maakt alles er mooi na de feiten door het bijsnijden uit of iets overlappend we doen of niet willen. Nu alleen maar om deze week te motiveren en echt, waar u kunt gaan, uiteindelijk, met computer science. Niet alleen na probleem set vier. Maar na de andere cursus of een hele curriculum het is verbazingwekkend wat je kunt doen deze dagen in termen van afbeeldingen in het bijzonder. Sommigen van u misschien dit gezien hebben stroomt rond online. Maar ik dacht dat ik je laten zien, voor slechts een paar minuten, een glimp van wat computertechnologie en wat CGI, computer graphics kunnen doen deze dagen met een bekend liedje en misschien film. [MUZIEK - LANA DEL RAY, "JONG EN MOOI] LUIDSPREKER 1: Het is gewoon een klein beetje geweldig, misschien wel, maar hoe alomtegenwoordig - [Applaus] LUIDSPREKER 1: Ik downloadde het gewoon. Maar het is echt geweldig, denk ik, net hoe alomtegenwoordig software en code en tools zoals deze werkelijk zijn. Dus dat is een voorproefje van de richting waar je kunt gaan. Oh, niet meer Appliance vandaag. Nou, dat is eigenlijk tragische timing gezien het punt dat ik probeerde te maken. Oke, dus laten we het lanceren Fusion opnieuw. Remind me later. Oke, en je zou hebben gekregen van een e-mail als een terzijde als je kreeg een merken als dat. Oke, zo herinneren dat vorige week we begonnen te schillen terug deze later bekend als string. snaar herinnert een gegevenstype dat is gedeclareerd in de CS50 bibliotheek. En het is een deel van de zijwieltjes die nu zal beginnen af ​​te nemen. Het was een nuttig begrip vroeg op. Maar nu het gaat om meer te halen interessante en krachtiger te eigenlijk zien dat onder de motorkap, een string is net wat, hebben we gezegd? Ja, dus het is een zogenaamde char *. En het * er geeft aan dat er een soort adres gaat. En dus als je zegt char * bedoel je gewoon een variabele waarvan de data type is een wijzer nu. Het feit dat er de ster er betekent gewoon dat je bent waarbij een zogenaamde pointer. En dat aanwijzer gaat blijkbaar slaan het adres van, van Natuurlijk, een char. Nu waarom is dit logisch? Nou, wat is een string onder de motorkap? Nou ja, voor enige tijd hebben we gezegd dat een string onder de motorkap is slechts h-e-l-l-o, bijvoorbeeld. Maar we hebben gesproken over dit als die in wezen een array. En een scala ziet er dan een beetje meer als dit, met elk van deze het nemen van een hap. En dan hebben we gezegd dat er iets speciaals hier terug, de backslash 0 of null-terminator. Dus al die tijd, dit hier is een string. Maar echt, een string eigenlijk een adres. En adressen, zoals we zullen zien, zijn vaak voorafgegaan door 0x volgens afspraak. Wat doet 0x duiden? Weet iemand? Dus het betekent gewoon hexadecimaal. Dus je zou kunnen herinneren, eigenlijk, van Pst 1, geloof ik, een van de warm-up vragen eigenlijk gesteld over hexadecimale notatie naast binair en decimaal. En de motivatie is dat met hexadecimale je hebt 16 cijfers tot uw beschikking. 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, gevolgd door a, b, c, d, e, f. En als je telt al die omhoog, krijg je een totaal van 16. Dus dit is in tegenstelling decimaal, waar we 10 cijfers, 0 tot en met negen. Het is in tegenstelling binaire waar we alleen maar 0 en 1. Maar aan het eind van de dag kun je gewoon geven dezelfde nummers, maar enigszins anders. En hexadecimale komt vaak omdat als het blijkt - en we zullen dit zien later in de cursus - zelfs als we de programmering, in de context van HTML en kleurcodes, hexadecimaal is leuk. Omdat elk cijfer, blijkt, vertegenwoordigt vier bits perfect. Dus het gewoon een soort lijnen mooi als we uiteindelijk zullen zien. Dus dit zou kunnen zijn Ox123 ofzo als dat, dat duidt op adres 123 ergens binnenkant van mijn het geheugen van de computer. Maar natuurlijk, een aantal problemen voordoen hierdoor onderliggende implementatie. En herinner me dat ik een gooi naar uitvoering van een functie als deze - vergelijk dash 0 dot c vorige week, dat hoewel het zag eruit alsof het was recht, het gewoon niet te vergelijken twee tekenreeksen correct. Ik heb weg belangrijkste geworpen, en ik heb gegooid weg de reacties alleen te concentreren in op de code dat is hier van belang. En het is in het rood omdat het buggy. Om welke reden? Nou, aan de top er toen ik verklaarde een string, wat er werkelijk aan de hand onder de motorkap? Nou, laat me over te gaan naar de screenen hier en teken dat. Dus verklaarde I, weer, tekenreeks s GetString. Dus ik ga om verder te gaan nu en tekenen s voor wat het werkelijk is. Het gaat om een ​​vierkant hier te zijn. En ik ga conclusie dat is 32 bits. Althans het meestal is, tenminste de CS50 apparaat in een veel computers. Ik ga het s noemen. Maar nu herinneren dat we riep GetString. Dus GetString rendement, natuurlijk een tekenreeks. Als de gebruiker typen in h-e-l-l-o invoeren de string hello wordt geretourneerd. En die string, zoals we net zeiden, eindigt ergens in het geheugen van uw computer met een backslash 0 eind. Ik zal deze tekenen als de matrix - of aaneengesloten blok tekens - dat het eigenlijk is. En nu, wat is getString eigenlijk terug? Wat is getString is terug al die tijd? Nou, we zeggen, in de weken voorafgaande, Het geeft een string. Maar meer technisch, wat doet GetString terugkeer blijkbaar? PUBLIEK: een adres. LUIDSPREKER 1: een adres. Concreet is het adres van het weer de eerste hap, wat het ook is. Ik blijf gewoon met behulp van een, twee, drie want het is handig. Het geeft het adres van de eerste teken in de reeks. En we vorige week gezegd dat dat volstaat. Omdat we altijd kunnen achterhalen waar het einde van de string alleen door itereren over het, misschien, met een voor lus of een tijdje lus of iets dergelijks dat, gewoon op zoek naar "backslash 0", de speciale sentinel karakter. En dan weten we dat de string gebeurt te zijn van de lengte - in dit geval - vijf. Dus technisch gezien wat GetString doet is het terugkeert Ox123 in dit geval. En technisch gezien wat er dan gebeurt is dat we slaan, de binnenkant van s, Ox123. Aan het eind van de dag, ook al wordt nieuw concept, pointers, zijn ze gewoon variabelen. Maar ze toevallig stukjes slaan dat vertegenwoordigen samen een adres. Dus technisch gezien alles wat ze krijgt opgeslagen in s is Ox123. Maar wij als mensen - waaronder vandaag verder - zijn echt niet van plan om de zorg, meestal, wat de werkelijke adres is van sommige brok van geheugen. Het is gewoon te lage niveau van detail te intellectueel interessant. Dus ik ga dit ongedaan te maken. En in plaats daarvan, meer hoog niveau, gewoon zeggen dat wanneer we praten over pointers Ik ga gewoon trekken meer gebruiksvriendelijke pijl dat brengt de hetzelfde idee en abstracts weg de bijzonderheden van wat de werkelijke onderliggende adres is. Nu als we terug gaan naar de code, wat gebeurde vorige week als we touwtje t gelijk getString? Nou, als ik weer, typt hello dit keer ga ik krijgen een ander stuk van het geheugen. h-e-l-l-o backslash 0. Maar omdat ik geroepen getString een tweede keer - en ik weet dit uit te kijken naar de broncode voor GetString - zelfs al is het toevallig dat hello was getypt in twee keer, GetString is niet gaan proberen te optimaliseren en slim zijn. Het gaat gewoon om een ​​ander stuk van krijgen het geheugen van de computer, dat is gaat worden op een ander adres. Laten we willekeurig maar zeggen 456. En wat gaat dat terug? Het gaat om 456 keren en opslaan in t. Dus wat er werkelijk aan de hand, op de linkerkant is ik heb een andere brok geheugen, typisch 32 bits. En daar zal gaan Ox456. Maar nogmaals, ik ben niet geïnteresseerd in deze bepaalde nummers niet meer. Ik ga gewoon om abstract tekenen het als een pijl. Dus dit is nu een nieuwe verklaring. Maar het is precies dezelfde gedachte dat is is gebeurd al die tijd. En dus de reden dan, dat deze eerste versie van vergelijken was buggy Vorige week is de reden waarom? Wanneer je doen als s gelijk gelijk t wat bent u werkelijk onder de motorkap te vergelijken? Je vergelijkt de adressen. En gewoon intuïtief, duidelijk, Ox123 is niet van plan om gelijke Ox456. Die nummers, die bits zijn gewoon anders. En zo consequent, vorige week zei het u verschillende dingen typt, zelfs indien de woorden waren letterlijk hetzelfde. Dus repareren we dit. In termen van de leek, wat was de oplossing? PUBLIEK: Gebruik een functie. LUIDSPREKER 1: Gebruik een functie. Of sterren zijn zeker betrokken, maar gebruik een functie om te doen wat? PUBLIEK: Om de snaren te vergelijken. LUIDSPREKER 1: Om de snaren te vergelijken. Zodat het fundamentele probleem hier was dat ik overwoog de kwaliteit van de snaren moet worden vastgesteld door vergelijking van hun adressen. En natuurlijk dat is gewoon dom nu eenmaal je begrijpt wat er gaande onder de motorkap. Om echt te vergelijken tekenreeksen om te zien of zij zijn gelijk in de manier waarop een mens zou overwegen twee snaren te gelijk zijn we nodig hebben om ze te vergelijken karakter voor karakter voor karakter. Nu kon ik heb gedaan deze zeer moeizaam. Maar vertrouwelijk, we zijn met behulp van een lus. En net vergelijken s beugel i tegen t beugel i. s beugel i plus 1 tegen t bracket i plus 1, enzovoort, binnen een soort lus. En als ik ter plaatse een twee personages die verschillen, of als ik besef dat ooh, s is t korter dan of langer dan t Ik kan meteen valse zeggen, ze zijn niet hetzelfde. Maar als ik via de s en t en zeggen: hetzelfde, hetzelfde, hetzelfde, hetzelfde, hetzelfde, eind beide strings, kan ik zeggen waar zij gelijk. Nou ja, gelukkig, jaren geleden iemand schreef dat de code voor ons. En ze noemden het StrComp voor strijkers vergelijken. En ook al is het een beetje teller intuïtief, StrComp retourneert 0 als deze twee strings, s en t dezelfde zijn. Maar het negatieve waarde geretourneerd als s moet komen voordat t alfabetisch of positieve waarde als het moet komen na t alfabetisch. Dus als je ooit iets wilt sorteren, het blijkt dat StrComp nuttig is. Omdat het niet alleen zeggen ja of nee, gelijk of niet. Het geeft je een gevoel van bestellen zoals een woordenboek macht. Dus StrComp, s komma t gelijk gelijk aan 0 betekent dat de strings zijn echt gelijk. Want wie deze functie schreef jaar geleden vermoedelijk gebruikt een lus of een while loop of iets dergelijks om opnieuw over de personages te integreren en weer. Maar probleem twee ontstond hier. Dit was copy0.c. En de twee in het rood is omdat het gebrekkig. En wat hebben we hier doen? Nou, eerst belde ik getString. En ik opgeslagen de return waarde in s. Dus dat is vrij veel het zelfde als Dit bovenste deel van het beeld. Maar wat komt daarna? Nou, laat me gaan en te ontdoen van een hele hoop van. We gaan in de tijd naar de plaats waar we gewoon terugspoelen s hebben, die nu is met lijn een daarboven. Ik check. Als s gelijk is gelijk aan 0. Nu, een snelle kanttekening, wanneer zou GetString terug 0? Er is niet genoeg geheugen. Rechts? Het is zeldzaam dat dit gaat gebeuren, zeker op een computer die is kreeg honderden meg of zelfs optredens van RAM-geheugen. Maar het kan, in theorie, terug 0, vooral als de gebruiker niet meewerken. Er is manieren te doen alsof je niet ingevoerde alles en trick GetString in terugkeer 0 effectief. Dus het gaat om te controleren dat. Want als iemand van jullie zijn begonnen krijgen, al, segmentatie fouten - die waarschijnlijk is een bron van wat frustratie - dat zijn bijna altijd het gevolg van geheugenfout. Een of andere manier je messed up met betrekking tot een wijzer, zelfs als je niet beseffen Er was een pointer. Dus zou je segmentatie hebben veroorzaakt fouten zo vroeg week een met behulp van iets als een lus of een tijdje lus en een array door te ver te gaan voorbij de grenzen van enkele array die u verklaard, in week twee in bijzonder. Je zou kunnen hebben het gedaan, zelfs in problemen set vier met Breakout. Ook al heb je waarschijnlijk niet hebt gezien alle sterren in de verdeelsleutel voor Breakout, het blijkt dat die GRect en Goval en andere dergelijke dingen, dat zijn eigenlijk pointers onder de motorkap. Maar Stanford, net als wij, soort van huiden dat detail in ieder geval voor de bibliotheken doeleinden, net zoals wij doen voor string en char *. Maar GRect en Goval en al die dingen jullie zijn of zullen worden met behulp van Deze week zijn uiteindelijk geheugenadressen. Je gewoon niet weten. Dus het is niet verwonderlijk dan, misschien, dat je zou struikelen sommige segmentatie fouten. Maar wat interessant is hier nu, Als na het controleren we voor 0 wij doen koord t krijgt s. Nou, laat me verklaren t. Ik ga om het te tekenen als een vierkant, 32 bits, noem het t. En dan ga ik doen krijgt s. Nou, wat betekent dat? Nou, het is een beetje moeilijk te denken over het beeld te verstandig. Maar laten we nadenken over wat er in x? Wat is letterlijk binnen deze variabele? De waarde Ox123. Dus als ik zeg koord t krijgt s, die net betekent letterlijk neemt het aantal in s, dat is Ox123 en zet het Ox123. Of picturaal, als ik soort van abstracte weg van dat detail heeft de effect van letterlijk doen dit ook. Dus nu, denk terug aan vorige week, toen we overgegaan tot kapitalistische T. I deed T beugel 0. Nou, T beugel 0, ook al is het een pointer, kunt u het alsof behandelen het is een array met een vierkant haakjesnotering. Dus waar is T beugel 0? Nou, het is de h. En dus als we die lijn van code, twee bovenste, die in dat c type.h header-bestand, dat is waar het wordt verklaard. Je bent kapitaliseren dit H. Maar van Natuurlijk, dat is precies dezelfde h dat is binnenkant van s, om zo te zeggen. En dus nu zijn gewijzigd of gekapitaliseerd zowel het origineel als de zogenaamde copy. Omdat u een kopie in de niet te maken manier waarop een mens zou willen dat het is. Dus wat is hier de oplossing, in copy1.c vorige week? Functies, dus konden we eigenlijk kopieert de string. En fundamenteel, wat hebben we nodig om doen om de string te kopiëren? Nou, in deze groene versie hier ben ik gaat het vrij lage niveau te doen. Er zijn eigenlijk functies ze kunnen helpen met dit. Maar de meest elementaire ene, en de meest vertrouwde een, op zijn minst, zal binnenkort vertrouwd voor ons, is het volgende - zodat men op de eerste regel van de code in het groen bedrijf. Ik herschreef s als char *. Er is geen functionele verschil is er. Ik gooide de CS50 bibliotheek weg en Ik noem het wat het is, een char *. Nu puntje, puntje, puntje, want er waren sommige foutcontrole dat is niet interessant om over praten weer. Dus nu t wordt verklaard. Het is ook een char *. Dus ik tekende een pleintje op het scherm als voorheen. Maar aan de rechterzijde, malloc, we zeiden is geheugen toe te wijzen. Zo wijzen sommige brok van geheugen. En hoeveel bytes eigenlijk doen wij wilt toewijzen, het lijkt? Nou, de string lengte van s. Dus als het hallo dat is gaat worden vijf. We zeggen h-e-l-l-o. Dus vijf bytes. Maar dan plus 1, waarom 1? De 0 karakter. Als we geen ruimte voor deze man die we misschien per ongeluk een situatie te creëren waarbij de string h-e-l-l-o. En dan de volgende keer GetString is riep en ik typ in, bijvoorbeeld, David, D-a-v-i-d, de computer gaat om te denken dat s is eigenlijk h-e-l-l-o-d-a-v-i-d omdat er geen pauze in tussen die woorden. Dus we moeten die pauze. Dus we willen niet vijf. We willen zes bytes. En bytes ik zeg. Maar het is echt tijd grootte van char. Technisch char is bijna altijd een byte. Maar alleen om onze code draagbaar te maken, zo te zeggen, zodat het werkt op verschillende computers, zelfs als ze zouden kunnen enigszins anders onder de hood, ik ga generiek Zeg grootte van char zodat mijn code altijd werken. En ik heb niet om het te compileren gewoon omdat ik mijn computer te upgraden of gebruik sommige ander platform. Dus ik heb 6 keer de grootte van een char, die toevallig 1. Dus dat betekent malloc kon geef me zes bytes. Wat is dat eigenlijk doen? Nou, laat me roll terug in de tijd hier tot waar we zijn in het verhaal. Dus als ik ga hier terug, heb ik verklaard een char * genaamd t. Ik heb nu genoemd malloc voor zes bytes. En nu ga ik die zes trekken bytes net als de array eerder. Maar ik eigenlijk niet weet wat er binnen deze array. Als u geheugen toe te wijzen blijkt dat je kunt niet vertrouwen dat er een aantal bekende waarde daar. Het zou kunnen zijn gebruikt door iets anders, een andere functie, een andere regel code die je schrijft. Dus we meestal noemen deze garbage waarden en teken ze, misschien, zoals vraagtekens, net wat aangeeft dat we weet niet wat er eigenlijk. En dat is geen groot probleem, zolang we zijn slim genoeg om die te overschrijven garbage waarden met cijfers of chars dat we de zorg over. Dus in dit geval wat ga ik doen? Nou, mijn lijn van code volgende, ik heb vier. int krijg ik 0, n krijgt de snaarlengte van s. Dus een vertrouwde lus. I kleiner is dan of gelijk aan n, die meestal boven. Maar deze keer is het bewuste. I + +, en dan moet ik gewoon doen t beugel i krijgt s. Omdat mijn foto ziet er als volgt bij dit ogenblik, opgeslagen in t is de adres van die willekeurig stuk van het geheugen waarvan de waarden zijn onbekend. Maar zodra ik doe t bracket 0 dat ik hier zet. En wat uiteindelijk er steeds opgesteld? We uiteindelijk zetten h. Want dat is wat er op het s beugel 0. En dan hetzelfde voor e, en l, en l, en o. n, waarom heb ik optrekken door een gelijk aan n? Door de 0 karakter. Dus gewoon om duidelijk te zijn, dan, als ik eigenlijk wist u alles wat deze garbage waarden zijn en vervolgens daadwerkelijk te tekenen in verwacht ik, is s beugel 1, 2, 3, 4, plus dat is trailing nieuw karakter. En dus nu als we verder langs de stip, dot, dot in deze juiste versie en gekapitaliseerde t beugel 0 zou ik, van Uiteraard worden kapitaliseren alleen deze man hier, die conceptueel, was uiteindelijk het doel. Dus dat is al de wijzer is. En je hebt ze te gebruiken voor weken nu in de context van de snaren. Maar onder de motorkap zijn ze een beetje ingewikkelder. Maar als je denkt over hen in deze picturale vorm Ik stel voor dat ze waarschijnlijk niet zo eng als ze misschien eerst lijken op het eerste gezicht, met name dergelijke nieuwe syntax. Heeft u vragen over pointers, strings of chars? Yeah? PUBLIEK: Kunt u terug te gaan aan de [onverstaanbaar]? LUIDSPREKER 1: Tuurlijk. PUBLIEK: Hoe komt het in je allerlaatste lijn, heb je niet een * t lijn en a * s in de lijn? Heb je niet de verwijzing naar de - LUIDSPREKER 1: Ah, een heel goede vraag. Waarom heb ik geen * t en a * s? Omdat kort, vorige week, net als in onze swap functie, heb ik gezegd dat als je hebt een pointer de middelen gekregen die je er zoals wij deden fysiek op het podium, zou eigenlijk Gebruik de ster operator. Het blijkt dat dit plein-bracket notatie is wat we syntactische zullen noemen suiker, dat is gewoon een sexy manier van zeggen dat het verkorte schrijfwijze voor precies wat je beschrijft. Maar het is een beetje meer intuïtief. En op het gevaar af van het maken van dit meer lijken ingewikkelder dan het moet zijn, wat er werkelijk aan de hand hier is de volgende - Als ik zeg * t dat betekent ga naar het adres opgeslagen in t. Dus letterlijk, als t wordt het opslaan het adres van die h aanvankelijk, * t middel gaan hier. Nu, wat doet t beugel 0 betekenen? Precies dezelfde dingen. Het is gewoon een beetje meer gebruikersvriendelijk vriendelijk te schrijven. Maar ik ben nog niet klaar. Ik kan niet zomaar zeggen * t krijgt * s. Want wat zou ik dan moeten doen? Ik zou zetten h, h, h, h, h gedurende de hele zaak. Rechts? Omdat * t is naar het adres in t. Maar we zijn binnen van een lus. En welke waarde moet ik verhogen, natuurlijk op elke iteratie? i. Maar er is een kans hier, toch? Hoewel dit voelt alsof het wordt steeds wat verfijndere dan de vierkante-haakjesnotering we hebben gebruikt voor enige tijd - laat me ongedaan mijn h verandering daar - ook al is dit nu een beetje krijgen liefhebber, het basisidee, indien * t betekent hier en * t is gewoon ga naar het adres in t. Maar wat was het adres in t? Het nummer dat we blijven gebruiken? Zoals Ox456, laten we brengen die terug alleen omwille van de discussie. Nou, als ik wil krijgen op de e in t touwtje, ik wil gewoon om te gaan, wezen, 456. Of liever gezegd, 457. Ik moet alleen een toe te voegen. Maar ik kan dat doen, toch? Omdat t, hoewel ik houd tekening Nu als een pijl, het is gewoon een nummer, Ox456. En als ik er een aan toevoegen, of meer over het algemeen, als ik voeg ik aan dat ik kan eigenlijk precies waar ik wil. Dus als ik dit eigenlijk doen - en dit is wat heet nu pointers - Ik kan deze lijn te verwijderen. Dat is, eerlijk gezegd, denk ik duidelijker en een beetje meer gebruikersvriendelijk te lezen. Maar dit is niet minder correct. Deze regel code nu is het gebruik van pointers. Het zegt naar de volgende adres - ongeacht de start van t, welke is t plus i, aanvankelijk is 0, wat geweldig is. Want dat betekent begin t plus 1, plus 2, plus 3, enzovoort. En dezelfde deal met s. Dus syntactische suiker voor. Maar begrijpen wat er werkelijk aan de hand onder de motorkap, zou ik pleiten, eigenlijk nuttig op zich. Want het betekent nu is er niet veel meer magie gaande onder de motorkap. Er zijn niet van plan om veel meer te zijn lagen die we kunnen schil terug voor u. Dit is c. En dit is het programmeren. Echt goede vraag. Oke, dus dit was dat buggy programma dat ik verwees naar eerder. swap was gebrekkig. Als leek te werken. Bedenk dat net als met de melk en het sinaasappelsap - waar ik begon het drinken van de demonstratie van vandaag. Dus net zoals met het sinaasappelsap en de de melk, hadden we een te gebruiken tijdelijke variabele, tmp, om een ​​te houden tijdelijk zodat we konden vervolgens zijn waarde veranderen en dan updaten b. Maar deze functie, zeiden we, of dit programma waarin deze functie was geschreven was verkeerd en gebrekkig, waarom? Ja? PUBLIEK: [onverstaanbaar]. LUIDSPREKER 1: Precies, wanneer je swap noemen - of meer in het algemeen, als je bel vrijwel elke functie - Als de argumenten om die functie zijn primitief, zo te zeggen, ints en chars en tweepersoonskamers en praalwagens, dingen zonder sterren, bent u passeren in een kopie van het argument. Als x 1 is en y is 2, een gaat zijn 1 en b zal worden 2. Maar ze gaan anders brokken bits, verschillende stukjes geheugen dat toevallig opslaan identieke waarden. Deze code is zo super perfect bij swapping a en b. Het is niet goed in te ruilen - in de afgelopen week bijvoorbeeld - x en y. Want nogmaals, ze zijn in de verkeerde scope. Nu, hoe zijn we gaan over de vaststelling van dit? We moesten om de functie te maken er een beetje lelijker. Maar nogmaals, overwegen wat Dit betekent gewoon. En eigenlijk, laat me, voor consistentie, veranderen een ding, dus het is identiek aan wat we net deden. Zoals ik al zei vorige week, is het niet uit waar het gaat. In feite, meestal zou je zet de ster naast de naam van de variabele. Maar ik denk dat het een beetje makkelijker de * overwegen naast de datatype die zin is het een pointer een int in dit geval. Dus wat doe ik hier? Ik zeg niet geef me een int gevolgd door een andere int ze a en b belt. Geef mij het adres van een int. Geef mij het adres van een andere int. Noemen deze adressen a en b. En vervolgens met behulp van de * notatie neer hieronder, naar elk van deze adressen als nodig is om ofwel of stel de waarde ervan. Maar er is een uitzondering hier. Waarom heb ik geen een * naast tmp? Waarom heb ik dit niet doen, bijvoorbeeld? Het voelt alsof ik moet gewoon gaan alle uit en corrigeer de hele zaak. Yeah? PUBLIEK: [onverstaanbaar]. LUIDSPREKER 1: Ik heb niet verklaard tmp als een string. Dus dit zou verklaren, in dit geval, een tmp aan het adres van een int zijn. Maar dat is niet helemaal wat ik wil, voor een paar redenen. PUBLIEK: Je wilt niet om ze te verwisselen. LUIDSPREKER 1: Precies, ik wil niet ruilen iets met tmp. tmp is gewoon week-een dingen. Alles wat ik wil is een variabele om enkele nummer op te slaan. Ik weet niet eens schelen adressen op dit moment. Ik moet alleen 32-bits of dus een int slaan. En ik wil zetten in die 32 bits alles wat niet in een, zo te zeggen, maar wat er op een, alleen maar om precies te zijn. Want als er een is een adres, * een middel ga er en krijgt de waarde 1. Bijvoorbeeld, in Bijvoorbeeld laatste week of in het geval b's, krijgen de waarde van 2. Dus wat er werkelijk aan de hand? Laat me een foto hier dat zal trekken alleen plagen elkaar een deel van vandaag. Maar dit zal blijven verschijnen al geruime tijd. Dit, ik beweer, is wat uw computer geheugen eruit ziet als je loopt een programma, een programma. Wanneer u een programma uitvoert aan de top RAM-geheugen van uw computer - dus denk aan deze rechthoek, echt, als uw RAM-geheugen of het geheugen van de computer, alle 101 miljard bytes van het, al twee miljard bytes, alle twee gigabyte ervan, ongeacht de hoeveelheid die je hebt is, laten we het tekenen als een rechthoek. En ik beweer dat wanneer u een programma uitvoert zoals Microsoft Word of Chrome of iets dergelijks, de bits die Microsoft of dat Google schreef - in het geval van deze programma's - worden geladen in het geheugen van uw computer waar ze meer kunnen worden uitgevoerd snel en toegevoerd aan de CPU, die is het brein van de computer. En in TAM ze helemaal aan het zijn opgeslagen top van uw programma, om zo te zeggen. Met andere woorden, als dit een brok geheugen, wanneer u dubbelklikt op Microsoft Word, de bits komen van de harde schijf. Ze krijgen in het geheugen geladen. En we zullen ze schuiven op naar de top de rechthoek conceptueel. Nou ja, de rest van je geheugen is voor verschillende dingen. Helemaal bovenaan zie je initialiseren gegevens en uninitialize gegevens. Dit hangt voor het grootste gedeelte, met constanten of globale variabelen die waarden. Maar meer op die andere tijd. Dan heb je de hoop, die we zullen terug te komen. Maar onder het deel dat bijzonder relevant nu. Het is de zogenaamde stack. Dus net als in vrijwel elke D hal hier op campus, heb je van die bakjes die alleen worden boven elkaar waarop u kunt eten en wat al gezet. De stack in een computersysteem is zeer vergelijkbaar. Behalve dat de lade, zoals we gebruiken in de eetzaal, natuurlijk, is bedoeld om dingen te dragen van de trays of de frames - zoals we ze zullen noemen - in een computer geheugen voor bewaring variabelen en waarden. Dus wat er werkelijk gebeurt onder de motorkap? Nou, laat me omdraaien naar het scherm hier. En laten we focussen alleen op de onderste deel voor een moment. Als dit het bodemgedeelte van mijn het geheugen van de computer het blijkt als ik bellen met de functie main - dat gebeurt, eerlijk gezegd, automatisch voor mij - Ik krijg een brok van het geheugen op de onderkant van mijn RAM zo te zeggen. En dit is waar de belangrijkste is lokale variabelen gaan. Het is waar argc en argv misschien gaan, en alle variabelen I verklaren binnenkant van de belangrijkste. Ze belanden op de bodem RAM-geheugen van mijn computer. Stel nu dat de belangrijkste gesprekken een functie zoals swap, zoals het deed vorige week? Nou, we wezen zet een nieuwe tray, een nieuw frame, op mijn stuk van het geheugen. En ik ga dit zo te beschrijven die behoren tot de swap-functie. Nu wat er in ruil? Nou ja, op basis van het programma van vorige week en degene die we zagen slechts een fragment uit, binnenkant van het frame swap's, of op swap's lade, zijn wat variabelen? Nou, a en b. Want dat waren de lokale argumenten, plus een derde tmp. Dus echt, ik kon dit tekenen een beetje schoner. Laat me ga je gang en maak de label. En laat me zeggen dat je weet wat? een is waarschijnlijk zal hier eindigen. B gaat hier eindigen. En tmp gaat hier eindigen. Nu, de bestelling zou een beetje anders. Maar conceptueel dit is het idee. En gezamenlijk dit wat we zullen frame van swap noemen, of eetzaal lade. En dezelfde deal met de belangrijkste. Maar ik zal niet opnieuw te tekenen dat. Maar dat is waar argc en argv en eventuele van zijn lokale variabelen zoals x en y kan net zo goed zijn. Dus nu overwegen wat er echt gebeurt als je swap bellen. Als je swap noemen, het uitvoeren van code zoals dit, je bent passeren in, in de buggy versie, a en b als kopieën van x en y. Dus als ik nu deze tekenen op het scherm - kreeg om beter te worden in deze - dus het verhaal dat ik vertelde mezelf In deze versie buggy, als we bel swap passeren in letterlijk a en b als gehele getallen, is wat er echt gebeurt? Nou, wat er echt gebeurt is dit. Laat me ga je gang en ongedaan net op te helderen wat ruimte hier. Dus dit is het geheugen van mijn computer. Dus als ik bijvoorbeeld - eigenlijk laten we het op deze manier - als ik beweren dat dit is x, opslaan de waarde 1 net als vorige week. Dit is y, opslaan van de waarde 2 net als vorige week. En dit is de belangrijkste, als ik bel swap, mezelf waardoor het geven van toegang tot een en b en tmp, ga ik om te beweren dat Dit is een en is 1. Dit is b. Dit is 2. Dit heet tmp. En in eerste instantie, het heeft een aantal vuilnis waarde totdat ik daadwerkelijk op te slaan in het een, die 1. Dan ga ik door en verandert een te zijn wat? B's waarde. En dus nu heb ik twee hier. En toen we zeiden b krijgt tmp. Opnieuw, net als een sanity check, de derde regel code hier is eenvoudig dit men, b krijgt tmp. En dus tot slot, wat moet ik doen? Ik ga door en verandert b te zijn wat de waarde van tmp is, die 1. Ik heb tmp niet meer aanraken. Maar nu het probleem zodra swap rendement, omdat het niet uitdelen back enige waarde, is er geen terugkeer verklaring expliciet erin. Wat is er eigenlijk gebeurt? Nou ja, in wezen al dit geheugen - OK, blijkbaar de gum houdt een vinger tegelijkertijd - gewoon verdwijnt. Nu in werkelijkheid is het niet gaat nergens heen. Maar je kunt het zien nu als vraagtekens. Want het is niet meer daadwerkelijk gebruikt. En er wordt niets gedaan met die waarden. Dus in het geval van de groene versie deze code, wat plaats is het zijn overgegaan in ruil? Zo richt. Zodat het adres van x en het adres van y. Dus als we opnieuw vertellen dit verhaal nog een laatste tijd, en ik eigenlijk opnieuw te tekenen swap, maar met pointers, hetgeen een, dit zijnde b, en dit is tmp, wat is feitelijk in een in deze groene versie van mijn code waar ik het passeren in adressen? Het gaat om een ​​pointer naar x te zijn. Zo kon ik een pijl te tekenen. Maar laten we gebruiken dezelfde arbitraire bijvoorbeeld als voorheen. Laten we zeggen dat dit iets als Ox123. En dit gaat worden Ox127 omdat het is vier bytes weg omdat het een int, dus Ox127. En nogmaals, ik ben het nemen van een aantal vrijheden met de nummers. Ze zijn veel kleiner dan ze zouden daadwerkelijk en in een andere volgorde. Maar dat is hoe het beeld is nu anders. Maar toen ik deze groene code en ik heb int tmp krijgen * een. * Een middel om het volgende te doen, neemt de pakken die in een en ga naar het, die 1. En dat is wat ik vervolgens in tmp. Ondertussen, in de volgende regel code Hier, * a krijgt b, wat betekent dat? Nou, * een, dus ga hier krijgt * b, wat betekent dat er heen gaan. En dat betekent dat de waarde naar daar. Ten slotte is de laatste regel code eenvoudig gezegd * b krijgt tmp. Dus b zegt dat er gaan en overschrijf met tmp die, in dit geval, gaat wil weer, 1. En dit is de reden waarom de groene versie van onze code werkt, terwijl de rode versie nooit gedaan. Het allemaal neer op hoe de geheugen wordt beheerd en waar het in uw daadwerkelijk geplaatst RAM van de computer. En voor nu, dat is een van de dingen dat de stapel wordt gebruikt. Vragen over de lay-out? Op pointers? Of op swap? Oke, dus malloc, rappel, deed iets als dit. Dit was een super eenvoudig voorbeeld. En dit was degene die Binky stelde ons voor aan, zij het vrij snel eind klasse. Dammit, daar gaan we weer. Zo herinneren dat dit het voorbeeld dat Binky stelde ons voor aan, zij het enigszins snel aan het einde van de les. En hier hebben we gebruik malloc echt voor de tweede keer. Omdat de eerste keer dat we gebruikten het om aan voldoende RAM, toewijzen genoeg RAM een tekenreeks slaan. Dit keer Binky het simpel gehouden. Dus het is om gewoon te slaan een int, blijkbaar. En dat is helemaal prima. Het is een beetje raar, eerlijk gezegd, om Gebruik malloc naar een int toe te wijzen. Maar het punt van Nick's claymation was eigenlijk alleen maar vertellen het verhaal van wat gebeurt of niet gebeurt wanneer je mishandelen geheugen. Dus in dit geval, het programma deed een paar dingen. In het eerste geval hier, het verklaart een pointer genaamd x naar een int. Het verklaart dan een pointer riep y naar een int. Het slaat dan in x, wat? Iemand anders nu. Wat er wordt opgeslagen in x volgens de derde regel van dit programma? PUBLIEK: [onverstaanbaar]. LUIDSPREKER 1: Nou, niet helemaal bytes, per zeggen. Wees nu nauwkeuriger. Wat er wordt opgeslagen in x? Een adres, ik denk dat ik het hoorde. Dus wat doet malloc terug? malloc gedragsmatig toewijst een stuk van het geheugen. Maar hoe werkt het geeft je toegang tot het? Het geeft wat? Het adres van de eerste byte in het stuk van het geheugen. Nu, dit is super simpel. Het is gewoon een byte, wat betekent dat de pakken we krijgen terug is de adres van de hele zaak. Dus opgeslagen in x dan is, is het adres van dat stuk van het geheugen. Ondertussen, wat gebeurt er nu? Dus eigenlijk, laten we verder gaan en trekken dit uit echt snel. Dus als we gaan over naar het scherm hier en we spelen dit uit int * x en int * y gaat wat voor mij doen? Ik eis dat het gewoon gaat doen zoiets als dit en noemen het x, en dit en noemen het y. Intussen is de derde regel van de code is naar de grootte van een int toewijzen die toevallig - sorry als ik zei - een voordat ik een int betekende vier bytes op een typische computer. In ieder geval met de CS50 apparaat. Dus dit gaat te wijzen het, wie weet? Ergens hier. En dit wordt opgeslagen bij sommige adres Ox, wie weet? Maar wat er gaat komen terug is dat adres. Maar we zullen dit picturaal trekken als net een pijl als dat. Nu in de volgende regel * x krijgt 42. Wat betekent * x betekenen in lekentaal? Ga gewoon daar. Ga naar dat adres. Of met andere woorden, volgen de pijl en zet 42 daar. Maar dan is er iets ergs gebeurd naar Binky, toch? Bedenk dat lijn vijf hier, * y krijgt 13, inderdaad een ongeluksgetal, deed wat voor ons? Nou, * y middelen gaan daar. Nou, dit is niet gegeven nog een waarde, toch? De code heeft geen y zijnde geïnitialiseerd tot niets. We hadden x geïnitialiseerd naar een adres. Maar y werd uitgeroepen tot top. Maar dan een puntkomma, geen waarde werd in het eigenlijk gezet. Dus het is eerlijk om deze te bellen een vuilnisbak waarde. Wie weet wat er staat? Het is de overblijfselen van bits die gebruikt werden wordt door eerdere regel code in mijn programma. Dus als ik zeg ga er, dit is als, Ik heb geen idee waar deze pijl is gaat uiteindelijk. En dat is wanneer je meestal krijgen een segmentation fault. Als u per ongeluk dereferentie, om zo te spreken, of ga naar een adres dat niet eigenlijk een legitiem adres, slechte dingen gebeuren. En dat is precies wat er gebeurd is naar Binky denken. Zodat herinneren dat het verhaal dat Nick was Hier vertellen was hetzelfde idee als wat Ik heb getekend met de illusie van krijt op het bord daar. X en Y zijn verklaard. Dan toegewezen we de grootte van een int en opgeslagen in x. Dan is de volgende regel hebben we * x. Dit was Nick's toverstaf van dereferentie. Dat zet 42 in het geheugen opgemerkt door x. Maar dit is waar de dingen ging vreselijk mis. Rechts? We hebben geprobeerd om dereferentie y. Maar y had een aantal nep-waarde, toch? Die pijl in de linker corner, is niet eigenlijk wijst naar iets. Het is een soort van te doen wat ik deed hier op het bord. Dus slechte dingen gebeuren, segmentatie storing of Binky fout, in dit geval. Maar als we vervolgens vast te stellen dat door het doen van x krijgt y hoe werkt het verhaal veranderen? Nou, als ik x krijgt y, dat is feite hetzelfde als zeggen wat het ook is, Ox-iets gaat hier hetzelfde, Ox-iets. Of picturaal we een pijl te tekenen. Dus hier op het bord met Binky, met de volgende regel van code, * y betekent gaan daar. Waar is er? Het betekent hier voorbij. En toen we een update van dat te zijn 13 het enkel gaat om te gaan en schrijven van 13 hier nu. Dus misschien niet helemaal eenvoudig op het eerste gezicht. Maar om samen te vatten en om hetzelfde jargon gebruiken dat Binky hier werd gebruikt, dus de eerste twee wijzen de wijzers, x en y, maar niet de pointees. En pointees is geen algemeen gebruikte term. Maar wijzer absoluut is. Maar het is wat er wordt gewezen op in de nomenclatuur van Binky's. Deze volgende lijn, natuurlijk, wijst een int pointee. Dus een stuk van het geheugen - zoals ik trok dan op de rechterzijde is er - en set x gelijk om te wijzen op het. Dit dereferences x op te slaan 42 in het geheugen dat het wijzend op. En dan deze, uiteraard, was een slechte zaak. Omdat y werd niet wijzen bij nog niets. Dit lost het. Dus dit is nog steeds buggy programma. Gewoon omdat we waait door de code lijn per lijn en zeggen, ach, laat het daar crashen. Dat is een slechte zaak. Odds zijn het programma zal alleen maar abort helemaal op die lijn. Maar als je te verwijderen van de gecrashte lijn en vervang deze door de laatste twee lijnen er u toewijst - behulp wijzer opdracht - y om te wijzen op x als punt t. En dan moet je dereferentie y in een zeer veilige manier. Dus waar komt dit ons verlaten? Nou, blijkt dat onder de motorkap in de CS50 bibliotheek, pointers zijn gebruikt in. En we daadwerkelijk beginnen te schillen terug die laag duurde niet lang. Maar het blijkt ook, een uitdrukking die sommigen van u misschien bekend zijn met, name comfortabeler, is eigenlijk dat een zeer populaire website, of stack overflow, deze dagen. Maar dit heeft eigenlijk heel technische betekenis. We weten nu wat een stack is. Het is als een stapel trays binnenkant van een eetzaal. Of binnenkant van uw computer geheugen its die frames die worden gebruikt door functies. Nou, het blijkt dat als gevolg van die zeer eenvoudige uitvoering van geheugen en de frames op de zogenaamde stack, kun je eigenlijk controle over te nemen van een computersysteem vrij gemakkelijk. U kunt inbreken in een systeem als mensen zoals wij onze code niet hebben geschreven bijzonder goed. Als mensen zoals wij gebruiken brokken van het geheugen of het gebruik arrays - nog meer in het algemeen - maar soms vergeten om het te controleren grenzen van ons aanbod zoals je misschien heb je soms, en herhaald veel te ver voorbij het einde van een array. In het beste geval, uw programma misschien net crashen. Segmentatie fout, soort van gênant. Niet geweldig, maar het is niet per se een enorm slechte zaak. Maar als je programma is eigenlijk op echte computers van gebruikers, als het draait op een website die daadwerkelijk willekeurige mensen op het internet raken, laten mensen veroorzaken slechte dingen op je code is over het algemeen niet een goede zaak, want betekent dus de gelegenheid om besturing van de computer. En dit is gaan kijken een beetje cryptisch. Maar ik dacht dat ik je schrikken met Dit laatste voorbeeld hier. Hier is een voorbeeld van de code. En er is een goede Wikipedia artikel dat loopt door dit in meer detail. Ik heb de belangrijkste op de bodem roeping foo, passeren in argv van 1. En dat is gewoon zo dat je kunt start het programma en doorgeven een willekeurige ingang. En dan foo wordt verklaard up top als het accepteren van een string, of meer Juist, een char *. Het verklaart dan een array van chars. Noem het een buffer, meer algemeen, van maat 12. Zo 12 chars kan passen binnen van de matrix c genoemd. En dan is het gebruik van deze nieuwe functie, dat is nieuw, maar niet moeilijk te begrijpen, geheugen kopiëren. Het kopieert het geheugen van de bar, die was de variabele n verleden, ongeacht de gebruiker getypt in argv 1 in c. Hoeveel bytes? De lengte van de string van de bar. Dus met andere woorden, als de gebruiker types h-e-l-l-o enter, de lengte van de string van hello is vijf. Dus vijf van die bytes gaat krijgen gekopieerd naar de array c genoemd, die is van maat 12. Maar wat de gebruiker typt in een veel langere woord dat is 13 tekens of 14 tekens of 100 tekens of meer? Waar gaan ze heen? Nou, dat frame, die lade in de eetzaal stack, ze gaan om er naartoe te gaan. En het is gewoon om te beginnen met het overschrijven andere dingen die al op die stapel, overvolle de stack, zo te zeggen. Dus pictorially, denk aan het op deze manier. Dit is slechts een kleurrijke versie van het beeld dat we hebben al getekend. Aan de onderkant, laten we zeggen, is de belangrijkste. En op de top, wat je nu ziet is het frame, kleur gecodeerd nu, voor een functie genaamd foo. Maar wat is interessant hier over foo is dat hier is het frame. Dus het is getrokken net zoals ik deed maar in lichtblauw. En nu dit is waar c beugel 0 gaat. En dit is waar c beugel 11 gaat eindigen. Met andere woorden, het gebeurt worden weergegeven als een vierkant. Maar als je gewoon blijven plopping bytes beneden - of chars - ze gaan eindigen up op locatie 0 helemaal naar boven tot 11 omdat het 0 geïndexeerd. Maar waar is de 13e teken gaat uiteindelijk? Waar is de 14e? Waar is de 50e teken gaat uiteindelijk? Het gaat om door te gaan naar beneden. Want ook al hebben we getekend de foto met de stapel opgroeien, de adressen, het blijkt, gaan van kleine adressen, kleine pointers, om grote adressen. Dus het blijft maar gaan omhoog en omhoog. Als types van de gebruiker hallo, dat is geweldig. Geen bug, geen probleem, iedereen is veilig. Maar als soorten de gebruiker in wat we zullen bellen hoor en wederhoor code, vertegenwoordigd generiek als een, aanval, aanval, aanval, aanval, wat er kan gebeuren? Nou, als alle van de input die de gebruiker getypt is niet zomaar een vriendelijke of beledigende tekenreeks. Het is eigenlijk een opeenvolging van karakters dat als je het gecompileerd, het is eigenlijk code. Misschien is het code die verwijdert alle bestanden op uw harde schijf of verstuurt spam of iets dergelijks. Merk op dat wat de sleutel hier is dat als de bad guy kregen geluk om overschrijven de rode brok van het geheugen - wat ik niet putten uit mijn foto maar deze Wikipedia foto hier heeft - haar zogenaamde retouradres. Wanneer het voedsel terug, toen swap rendementen, hoe werkt de computer weten om te gaan van tot hier tot hier beneden? Of in de tech segment boven, hoe weet zij om te gaan van de swap code - de 0 en 1's dat swap componeren - terug naar main? Er is een zogenaamde retouradres opgeslagen in dezelfde stackframe op dezelfde cafetaria lade. Dus als de bad guy is slim genoeg om zet aanval code, aanval code, aanval code, en krijg het geluk - vaak door middel van trial and error - tot overschrijven die rode retouradres, met het adres en de mededeling de top. Merkt 0835C080. Het is geschreven achteruit up top voor redenen zullen we misschien opnieuw. Dit is het getal. Dus als de bad guy krijgt geluk of is slim genoeg om de rode overschrijven strippen van het geheugen met het adres van code die hij of zij heeft een of andere manier geïnjecteerd in uw computer, raden wiens code zal worden teruggestuurd naar Zodra foo gebeurt uitvoeren? Code van de bad guy's. Dus deze aanval code, AAA, nogmaals, misschien spam versturen, worden mogelijk niet alle bestanden verwijderen op uw harde schijf. Maar dat is wat echt een stack overflow is, of een buffer overrun, of een buffer overflow aanval. En het is ongelooflijk, ongelooflijk gemeenschappelijke tot op de dag met programma's geschreven in C, C + +, en zelfs andere talen. Op die enge opmerking, zullen we eindigen met een grap. [Lachen] Tot ziens op woensdag. Bij de volgende CS50 - Dus ik ben allen uit schijf lampen vandaag maar wacht, vetvrije melk, de helft van de telefoon boek, het sinaasappelsap dat ik vandaag dronk. USB-kabel, een moersleutel. [Muziek]