[Powered by Google Translate] [CS50 Bókasafn]
[Nate Hardison] [Harvard University]
[Þetta er CS50. CS50.TV]
The CS50 Bókasafnið er gagnlegt tól sem við höfum upp á tækinu
til að gera það auðveldara fyrir þig að skrifa forrit sem hvetja notendur til inntak.
Í þetta myndband, munum við draga til baka fortjald og líta á hvað nákvæmlega er í CS50 bókasafn.
>> Í myndbandinu á C bókasöfnum, tala við um hvernig þú setur # hausa skrár
safnsins í fengið þinn kóða,
og þá tengja með a tvöfaldur bókasafn skrá á tengja áfanga
í samantekt aðferð.
Hausinn skrá tilgreina tengi bókasafn.
Það er, þeir ítarlega öll þau úrræði sem bókasafnið hefur í boði fyrir þig að nota,
eins og yfirlýsingar virka, fastar, og gögn gerðum.
Tvöfaldur bókasafn skrá inniheldur framkvæmd safninu,
sem eru unnar upp úr skrám haus safnsins og safnsins. c kóðann skrá.
>> Tvöfaldur bókasafn skrá er ekki mjög áhugavert að horfa á þar sem það er, vel, í tvöfaldur.
Svo skulum við taka a líta á haus skrá fyrir bókasafn í staðinn.
Í þessu tilfelli, það er bara einn haus skrá heitir cs50.h.
Við höfum sett það í the notandi eru skrá
ásamt skrá haus hinna Bókasöfn kerfisins.
>> Einn af the fyrstur hlutur þú munt taka eftir er að cs50.h # felur haus skrár frá öðrum bókasöfnum -
fljóta, mörk, staðall bool, og staðall lib.
Aftur, eftir meginreglunni um ekki reinventing hjólinu,
Við höfum byggt á CS0 bókasafn með verkfæri sem önnur veitti okkur.
>> The næstur hlutur sem þú munt sjá í safninu er að við að skilgreina nýja tegund heitir "band."
Þessi lína í raun bara skapar alias fyrir char * tegund,
svo það er ekki dularfullur gæða nýja taginu String með eiginleika
almennt í tengslum við hluti band í öðrum tungumálum,
eins og lengd.
Ástæðan sem við höfum gert er að verja nýja forritari frá Gory smáatriði
af ábendingum þar til þau eru tilbúin.
>> Í næsta hluta af haus skrá er yfirlýsing um aðgerðir
að CS50 bókasafn veitir ásamt gögnum.
Takið eftir hversu ítarlega í athugasemdum hér.
Þetta er frábær mikilvægt svo að fólk veit hvernig á að nota þessar aðgerðir.
Við lýsum yfir, aftur á móti, aðgerðir til að hvetja notandann og aftur chars, tveggja manna, fljóta, ints,
lengi þráir, og strengi með eigin band tegund okkar.
Eftir meginreglunni um felum upplýsinga,
við höfum sett skilgreiningu okkar á sérstakri c framkvæmd skrá -. cs50.c--
staðsett í uppspretta notandi skrá.
Við höfum veitt að skrá þannig að þú getur tekið að líta á það,
læra af henni, og laun því á mismunandi vélar ef þú vilt,
jafnvel þó að við teljum að það er betra að vinna á tækinu í þennan flokk.
Engu að síður, við skulum taka a líta á það núna.
>> Hlutverk GetChar, GetDouble, GetFloat, GetInt, og GetLongLong
eru öll byggð ofan á GetString virka.
Það kemur í ljós að þeir fylgja öllum meginatriðum sama mynstur.
Þeir nota while lykkju til að hvetja notandann til að eina línu af inntak.
Þeir aftur sérstakt gildi ef notandi inntak tóma línu.
Þeir reyna að flokka inntak notandans sem viðeigandi tegund,
vera það bleikju, tvöfalda, sem fljóta, o.fl.
Og þá aftur annaðhvort niðurstöðu ef inntak var að flokka
eða þeir reprompt notanda.
>> Á háu stigi, það er ekkert mjög erfiður hérna.
Þú gætir hafa skrifað álíka Structured númer sjálfur í fortíðinni.
Kannski er mest Cryptic-útlit leyti sscanf kalla sem flokka inntak notandans.
Sscanf er hluti af snið inntak viðskipti fjölskyldu.
Hún býr í venjulegu io.h, og starf hans er að flokka C band,
samkvæmt tilteknu formi, geyma flokka niðurstöður á breytilegum
hjá þeim sem hringir.
Þar sem snið inntak viðskipti aðgerðir eru mjög gagnlegar, mikið notað virka
sem eru ekki frábær innsæi í fyrstu,
Við munum fara yfir hvernig sscanf virkar.
>> Fyrsta rök til sscanf er char * - bendi á staf.
Til að virka til að vinna almennilega,
þessi karakter ætti að vera fyrsti stafurinn í C band,
sagt við null \ 0 staf.
Þetta er band til að flokka
Seinni rök til sscanf er snið band,
venjulega framhjá í sem streng fasti,
og þú gætir hafa séð band eins og þetta áður þegar printf.
A prósent skilti í sniðstreng táknar viðskipti specifier.
Táknið eftir strax prósent skilti,
táknar C gerð sem við viljum sscanf að breyta til.
Í GetInt, sérðu að það er% d og% c.
Þetta þýðir að sscanf mun reyna að tugabrot int -% d - og char - the% c.
Fyrir hver viðskipti specifier í sniðstreng,
sscanf ráð samsvarandi rök síðar í listanum rök hennar.
Þessi rök að benda til viðeigandi slegið stað
til þess að geyma niðurstöðu í viðskiptum.
>> Dæmigerður leið til að gera þetta er að búa til breytu á mánudaginn fyrir sscanf kalla
fyrir hvern hlut sem þú vilt flokka af streng
og þá nota heimilisfang rekstraraðila - að merkið - til að fara framhjá ábendingum
að þeim breytum til sscanf stendur.
Þú getur séð það í GetInt við gerum einmitt þetta.
Rétt fyrir sscanf símtali lýsa við að int kallast N og char kalla c á mánudaginn,
og við framhjá ábendingum til þeirra í sscanf stendur.
Setja þessar breytur á stafla er valinn yfir með rúm úthlutað
á hrúga með malloc, þar sem þú forðast the kostnaður af malloc símtali
og þú þarft ekki að hafa áhyggjur af leka minni.
Stafir ekki forskeyti með prósent skilti ekki hvetja ekki viðskipti.
Frekar þeir bæta bara við snið forskrift.
>> Til dæmis, ef snið band í GetInt voru% d í staðinn,
sscanf myndi leita að bréfinu og fylgt eftir með int,
og á meðan það væri að reyna að breyta int, myndi það ekki gera neitt annað með A.
Eina undantekningin á þessu er stafabil.
White stafir pláss í sniðstreng passa hvaða magn af bil -
jafnvel ekkert á alla.
Svo, það er hvers vegna athugasemd nefnir hugsanlega með leiðandi og / eða slóð bil.
Svo á þessum tímapunkti það lítur út eins og símtal sscanf okkar munu reyna að flokka inntak band notanda
með því að haka fyrir mögulega leiðandi bil,
fylgt eftir með INT sem verður breytt og geymt í int breytunni n
eftir talsverða bil, og á eftir eðli
geymd í bleikju breytilegum c.
>> Hvað um aftur gildi?
Sscanf munu flokka inntak línu frá upphafi til enda,
hætt þegar það kemur að enda eða þegar staf í inntak
ekki passa snið staf eða þegar það getur ekki gert viðskipti.
Skilagildi Það er notað til einstaklings þegar það stöðvast.
Ef það hætt, því það náði í lok inntak band
áður en allir viðskipti og áður ekki að passa hluta af sniði band,
þá sérstakur fasti EOF er skilað.
Annars skilar það fjölda af farsælum viðskiptum,
sem gæti verið 0, 1 eða 2, þar sem við höfum beðið um tvo viðskipta.
Í okkar tilviki, við viljum tryggja að notandinn slegið í int og aðeins Int.
>> Svo viljum við sscanf að skila 1. Sjá hvers vegna?
Ef sscanf aftur 0, þá voru engin viðskipti gert,
þannig að notandinn slegið eitthvað annað en INT í upphafi inntak.
Ef sscanf skilar 2, þá notandinn ekki rétt að slá það inn á í upphafi inntak,
en þeir slegið þá í sumum ekki bil staf eftir
þar sem% C viðskipti tekist.
Vá, það er alveg langur skýring einn virka símtalinu.
Engu að síður, ef þú vilt frekari upplýsingar um sscanf og systkini hennar,
kíkja á síðum, Google, eða bæði.
There ert hellingur af sniðstreng valkostur,
og þessi geta spara þú a einhver fjöldi af handbók vinnuafli þegar reynt var að flokka strengi í C.
>> Endanleg aðgerð á safninu til að líta á er GetString.
Það kemur í ljós að GetString er erfiður virka að skrifa almennilega,
jafnvel þó það virðist eins og svo einfalt, sameiginleg verkefni.
Hvers vegna er þetta málið?
Jæja, við skulum hugsa um hvernig við ætlum að geyma línuna sem notandinn slær inn
Þar sem strengur er röð chars,
við gætum vilja til að geyma það í fylki á mánudaginn,
en við þyrftum að vita hversu lengi array er að fara að vera þegar við lýsa það.
Sömuleiðis, ef við viljum setja hana á hrúga,
við þurfum að fara að malloc fjölda bæti við viljum áskilja,
en þetta er ómögulegt.
Við höfum ekki hugmynd um hversu margir chars notandinn verður gerð í
áður en notandi í raun er gerð þá.
>> A barnaleg lausn á þessu vandamáli er bara að panta stór klumpur af rúm, segja,
blokk af 1000 chars um inntak notandans,
gert ráð fyrir að notandi myndi aldrei slá í streng að lengd.
Þetta er slæm hugmynd af tveimur ástæðum.
Fyrst, að því gefnu að notendur yfirleitt ekki slá ekki í strengi sem lengi,
þú gætir sóa a einhver fjöldi af minni.
Á nútíma vél, þetta gæti ekki verið málið ef þú gerir þetta
í einum eða tveimur einangruðum tilvikum,
en ef þú tekur notandi inntak er í lykkju og geyma til síðari nota,
þú getur auðveldlega sjúga upp tonn af minni.
Að auki, ef forritið sem þú ert að skrifa er í minni tölvu -
Tæki eins og a smartphone eða eitthvað annað með takmarkaða minni -
Þessi lausn mun valda vandræðum mikið hraðar.
Annað, meira alvarleg ástæða að ekki gera þetta er að það fer program viðkvæmt
hvað er kallað gnægð biðminni árás.
Í forritun, biðminni er minni er notað til að geyma inntak eða úttak gögn,
sem í þessu tilfelli er 1000-stafir blokk okkar.
A biðminni flæða stað þegar gögn eru skrifuð framhjá lok blokk.
>> Til dæmis, ef notandi í raun er gerð í meira en 1000 tákn.
Þú gætir hafa upplifað þetta óvart þegar forritun með fylki.
Ef þú ert með fjölda 10 ints, ekkert stoppar þig frá að reyna að lesa eða skrifa
15. int.
Það eru engar þýðanda viðvaranir eða villur.
The Program blunders bara beint áfram og aðgangur minni
þar sem það telur 15 int verður, og þetta getur skrifa aðrar breytur.
Í versta tilfelli getur þú skrifa sumir af innri forritinu er
Stjórntæki, veldur forrit til raunverulega framkvæma mismunandi leiðbeiningar
en þú ætlaðir.
>> Nú er það ekki algengt að gera þetta óvart,
en þetta er nokkuð algengt tækni sem slæmur krakkar nota til að brjóta forrit
og setja illgjarn merkjamál á tölvum annarra.
Þess vegna getum við ekki bara notað barnaleg lausn okkar.
Við þurfum a vegur til koma í veg fyrir áætlanir okkar frá því að vera viðkvæm
að flæða biðminni árás.
Til að gera þetta þurfum við að ganga úr skugga um að biðminni okkar geta vaxið eins og við lesum
meira inntak frá the notandi.
The lausn? Við notum úthlutað hrúga biðminni.
Þar sem við getum búa hana með að breyta stærð realloc virka,
og við höldum utan um tvær tölur - vísitölu næsta tómur rifa í biðminni
og lengd eða getu biðminni.
Við að lesa í chars frá notanda í einu með því að nota fgetc virka.
The röksemd fgetc virka tekur - stdin - er vísað til staðlaða inntak band,
sem er preconnected inntak rás sem er notuð til að flytja inntak notandans
frá flugstöðinni til the program.
>> Þegar notandi slær inn nýja persónu, athuga við að sjá hvort vísitala
af næstu frjáls rifa plús 1 er meiri en getu biðminni.
The +1 kemur í því ef að næsta frjáls vísitalan er 5,
þá lengd Buffer okkar verður 6 takk 0 flokkun.
Ef við höfum keyrt út af pláss í biðminni, þá erum við að reyna að búa það,
tvöföldun það svo að við skera niður á the tala af sinnum sem við búa
ef notandi er að skrifa í mjög langan streng.
Ef strengur hefur fengið of langt eða ef við keyra út af minni hrúga,
við frjáls biðminni okkar og skila NULL.
>> Að lokum, bæta við að bleikju í biðminni.
Þegar notandi smellir inn eða aftur, merkja nýja línu,
eða sérstökum stafir - stjórn D - sem merki enda á inntak,
Við gera a athuga hvort notandinn í raun slegið á eitthvað.
Ef ekki, aftur við null.
Annars, þar biðminni okkar er líklega stærra en við þurfum,
í versta falli það er næstum tvisvar sinnum eins og stór eins og við þurfum
þar sem við tvöfalda hvert skipti við breyta,
við tökum nýtt eintak af the band með bara pláss sem við þurfum.
Við bæta við auka 1 við malloc símtalið
þannig að það er pláss fyrir sérstökum null Terminator karakterinn - á \ 0,
sem við bæta við streng þegar við afrita í the hvíla af the stafi,
nota strncpy stað strcpy
svo að við getum tilgreina nákvæmlega hversu margir chars við viljum afrita.
Strcpy eintök þar til hann lendir á \ 0.
Þá erum við að losa biðminni okkar og skila afrit til þess sem hringir.
>> Hver vissi svo einfalt virtist virka gæti verið svo flókið?
Nú þú veist hvað fer í CS50 bókasafn.
>> Ég heiti Nate Hardison, og þetta er CS50.
[CS50.TV]