Tải bản đầy đủ - 0 (trang)
Chapter 4.  Arrays and Pointers

Chapter 4.  Arrays and Pointers

Tải bản đầy đủ - 0trang

Arrayshavesignificantdrawbackscomparedtovectors:They

arefixedsize,andtheyoffernohelptotheprogrammerin

keepingtrackofhowbigagivenarrayis.Thereisnosize

operationonarrays.Similarly,thereisnopush_backto

automaticallyaddelements.Ifthearraysizeneedstochange,

thentheprogrammermustallocateanew,largerarrayand

copytheelementsintothatnewspace.

Programsthatrelyonbuilt-inarraysratherthanusingthe

standardvectoraremoreerror-proneandharderto

debug.



Priortotheadventofthestandardlibrary,C++programsmade

heavyuseofarraystoholdcollectionsofobjects.ModernC++

programsshouldalmostalwaysusevectorsinsteadofarrays.

Arraysshouldberestrictedtotheinternalsofprogramsand

usedonlywhereperformancetestingindicatesthatvectors

cannotprovidethenecessaryspeed.However,therewillbea

largebodyofexistingC++codethatreliesonarraysforsome

timetocome.Hence,allC++programmersmustknowabit

abouthowarrayswork.



4.1.Arrays

Anarrayisacompoundtype(Section2.5,p.58)thatconsists

ofatypespecifier,anidentifier,andadimension.Thetype

specifierindicateswhattypetheelementsstoredinthearray

willhave.Thedimensionspecifieshowmanyelementsthearray

willcontain.

Thetypespecifiercandenoteabuilt-indataorclasstype.

Withtheexceptionofreferences,theelementtypecan

alsobeanycompoundtype.Therearenoarraysof

references.



4.1.1.DefiningandInitializingArrays

Thedimensionmustbeaconstantexpression(Section2.7,p.

62)whosevalueisgreaterthanorequaltoone.Aconstant

expressionisanyexpressionthatinvolvesonlyintegralliteral

constants,enumerators(Section2.7,p.62),orconstobjectsof

integraltypethatarethemselvesinitializedfromconstant

expressions.Anonconstvariable,oraconstvariablewhosevalue

isnotknownuntilruntime,cannotbeusedtospecifythe

dimensionofanarray.

Thedimensionisspecifiedinsidea[]bracketpair:

//bothbuf_sizeandmax_filesareconst

constunsignedbuf_size=512,max_files=20;

intstaff_size=27;//nonconst



constunsignedsz=get_size();//constvaluenotknown

charinput_buffer[buf_size];//ok:const

stringfileTable[max_files+1];//ok:constantexpression

doublesalaries[staff_size];//error:nonconst

inttest_scores[get_size()];//error:nonconst

intvals[sz];//error:size



Althoughstaff_sizeisinitializedwithaliteralconstant,staff_size

itselfisanonconstobject.Itsvaluecanbeknownonlyatrun

time,soitisillegalasanarraydimension.Eventhoughsizeisa

constobject,itsvalueisnotknownuntilget_sizeiscalledatrun

time.Therefore,itmaynotbeusedasadimension.Onthe

otherhand,theexpression

max_files+1



isaconstantexpressionbecausemax_filesisaconstvariable.

Theexpressioncanbeandisevaluatedatcompiletimetoa

valueof21.



ExplicitlyInitializingArrayElements

Whenwedefineanarray,wecanprovideacomma-separated

listofinitializersforitselements.Theinitializerlistmustbe

enclosedinbraces:

constunsignedarray_size=3;

intia[array_size]={0,1,2};



Ifwedonotsupplyelementinitializers,thentheelementsare



initializedinthesamewaythatvariablesareinitialized(Section

2.3.4,p.50).

Elementsofanarrayofbuilt-intypedefinedoutsidethe

bodyofafunctionareinitializedtozero.

Elementsofanarrayofbuilt-intypedefinedinsidethebody

ofafunctionareuninitialized.

Regardlessofwherethearrayisdefined,ifitholds

elementsofaclasstype,thentheelementsareinitialized

bythedefaultconstructorforthatclassifithasone.Ifthe

classdoesnothaveadefaultconstructor,thentheelements

mustbeexplicitlyinitialized.

Unlessweexplicitlysupplyelementinitializers,the

elementsofalocalarrayofbuilt-intypeareuninitialized.

Usingtheseelementsforanypurposeotherthanto

assignanewvalueisundefined.



Anexplicitlyinitializedarrayneednotspecifyadimension

value.Thecompilerwillinferthearraysizefromthenumberof

elementslisted:

intia[]={0,1,2};//anarrayofdimension3



Ifthedimensionsizeisspecified,thenumberofelements

providedmustnotexceedthatsize.Ifthedimensionsizeis

greaterthanthenumberoflistedelements,theinitializersare



usedforthefirstelements.Theremainingelementsare

initializedtozeroiftheelementsareofbuilt-intypeorby

runningthedefaultconstructoriftheyareofclasstype:



constunsignedarray_size=5;

//Equivalenttoia={0,1,2,0,0}

//ia[3]andia[4]defaultinitializedto0

intia[array_size]={0,1,2};

//Equivalenttostr_arr={"hi","bye","","",""}

//str_arr[2]throughstr_arr[4]defaultinitializedtotheemptys

stringstr_arr[array_size]={"hi","bye"};



CharacterArraysAreSpecial

Acharacterarraycanbeinitializedwitheitheralistofcommaseparatedcharacterliteralsenclosedinbracesorastringliteral.

Note,however,thatthetwoformsarenotequivalent.Recall

thatastringliteral(Section2.2,p.40)containsanadditional

terminatingnullcharacter.Whenwecreateacharacterarray

fromastringliteral,thenullisalsoinsertedintothearray:

charca1[]={'C','+','+'};//

charca2[]={'C','+','+','\0'};//

charca3[]="C++";//nullterminatoraddedautomatically



Thedimensionofca1is3;thedimensionofca2andca3is4.Itis

importanttorememberthenull-terminatorwheninitializingan

arrayofcharacterstoaliteral.Forexample,thefollowingisa

compile-timeerror:

constcharch3[6]="Daniel";//error:Daniel



Whiletheliteralcontainsonlysixexplicitcharacters,the

requiredarraysizeissevensixtoholdtheliteralandoneforthe

null.



NoArrayCopyorAssignment

Unlikeavector,itisnotpossibletoinitializeanarrayasacopy

ofanotherarray.Norisitlegaltoassignonearraytoanother:



intia[]={0,1,2};//ok:arrayofints

intia2[](ia);//error:cannotinitializeonearraywithan

intmain()

{

constunsignedarray_size=3;

intia3[array_size];//ok:butelementsareuninitialized!



ia3=ia;//error:cannotassignonearraytoano

return0;

}



Somecompilersallowarrayassignmentasacompiler

extension.Ifyouintendtorunagivenprogramonmore

thanonecompiler,itisusuallyagoodideatoavoidusing

nonstandardcompiler-specificfeaturessuchasarray

assignment.



Caution:ArraysAreFixedSize

Unlikethevectortype,thereisnopush_backorotheroperationtoadd

elementstothearray.Oncewedefineanarray,wecannotaddelements

toit.

Ifwemustaddelementstothearray,thenwemustmanagethe

memoryourselves.Wehavetoaskthesystemfornewstoragetohold

thelargerarrayandcopytheexistingelementsintothatnewstorage.

We'llseehowtodosoinSection4.3.1(p.134).



ExercisesSection4.1.1

Assumingget_sizeisafunctionthattakesnoargumentsand

returnsanintvalue,whichofthefollowingdefinitionsareillegal?

Explainwhy.

unsignedbuf_size=1024;

Exercise

4.1: (a)intia[buf_size];

(b)intia[get_size()];

(c)intia[4*7-14];

(d)charst[11]="fundamental";



Whatarethevaluesinthefollowingarrays?

stringsa[10];

intia[10];

Exercise intmain(){

4.2: stringsa2[10];

intia2[10];

}



Which,ifany,ofthefollowingdefinitionsareinerror?

(a)intia[7]={0,1,1,2,3,5,8};

Exercise (b)vectorivec={0,1,1,2,3,5,8};

4.3: (c)intia2[]=ia1;

(d)intia3[]=ivec;



Exercise

Howcanyouinitializesomeoralltheelementsofanarray?

4.4:

Exercise

Listsomeofthedrawbacksofusinganarrayinsteadofavector.

4.5:



4.1.2.OperationsonArrays

Arrayelements,likevectorelements,maybeaccessedusingthe

subscriptoperator(Section3.3.2,p.94).Liketheelementsofa

vector,theelementsofanarrayarenumberedbeginningwith0.

Foranarrayoftenelements,thecorrectindexvaluesare0

through9,not1through10.

Whenwesubscriptavector,weusevector::size_typeasthetype

fortheindex.Whenwesubscriptanarray,therighttypetouse

fortheindexissize_t(Section3.5.2,p.104).

Inthefollowingexample,aforloopstepsthroughthe10

elementsofanarray,assigningtoeachthevalueofitsindex:

intmain()

{

constsize_tarray_size=10;

intia[array_size];//10ints,elementsareuninitialized

//loopthrougharray,assigningvalueofitsindextoeachelement

for(size_tix=0;ix!=array_size;++ix)

ia[ix]=ix;

return0;

}



Usingasimilarloop,wecancopyonearrayintoanother:

intmain()

{

constsize_tarray_size=7;

intia1[]={0,1,2,3,4,5,6};

intia2[array_size];//localarray,elementsuninitialized

//copyelementsfromia1intoia2



for(size_tix=0;ix!=array_size;++ix)

ia2[ix]=ia1[ix];

return0;

}



CheckingSubscriptValues

Aswithbothstringsandvectors,theprogrammermust

guaranteethatthesubscriptvalueisinrangethatthearrayhas

anelementattheindexvalue.

Nothingstopsaprogrammerfromsteppingacrossanarray

boundaryexceptattentiontodetailandthoroughtestingofthe

code.Itisnotinconceivableforaprogramtocompileand

executeandstillbefatallywrong.

Byfar,themostcommoncausesofsecurityproblemsare

so-called"bufferoverflow"bugs.Thesebugsoccurwhen

asubscriptisnotcheckedandreferenceismadetoan

elementoutsidetheboundsofanarrayorothersimilar

datastructure.



4.2.IntroducingPointers

Justaswecantraverseavectoreitherbyusingasubscriptoran

iterator,wecanalsotraverseanarraybyusingeithera

subscriptorapointer.Apointerisacompoundtype;apointer

pointstoanobjectofsomeothertype.Pointersareiteratorsfor

arrays:Apointercanpointtoanelementinanarray.The

dereferenceandincrementoperators,whenappliedtoapointer

thatpointstoanarrayelement,havesimilarbehavioraswhen

appliedtoaniterator.Whenwedereferenceapointer,weobtain

theobjecttowhichthepointerpoints.Whenweincrementa

pointer,weadvancethepointertodenotethenextelementin

thearray.Beforewewriteprogramsusingpointers,weneedto

knowabitmoreaboutthem.



Tài liệu bạn tìm kiếm đã sẵn sàng tải về

Chapter 4.  Arrays and Pointers

Tải bản đầy đủ ngay(0 tr)

×