lalibrera<cstdlib>. Elmanejodelamemoriaheapsehaceconmalloc()yfree().EnC++estasfuncionesson reemplazadasporlaspalabrasclavenewydeleteloscualesimplementanseguridaddetipos. Paraborrararrayslasintaxisesdelete[]var Esposibledefinirvariablesenelbloquedeinicializacindeunainstruccinfor().Esusado bsicamenteparadefinirlasvariablesqueiteranenellazo. Sibienesposibleutilizarlosmtodosantiguosdecastcomo(nuevotipo)expresin,C++ definenuevosmtodosdecambiareltipoquesonmsseguros.Unodeelloses static_cast<nuevotipo>(expresin) AendlselollamamanipuladordeI/Oqueespecificacambiaralaprximalneaenun ostream. EnClosparmetrossonsolopasadosporvalor,esdecirquesehaceunacopiadelos valoresquesepasanalafuncinycualquiercambioenlosparmetrosdentrodelafuncinse pierdenalsalirdelamisma. int*idebeserleidocomoiesunpunteroaunint.Siluegoseencuentraconlaexpresin*i= 1enesecasoel*esunadereferencia,loquedebeleersecomoelintapuntadopori. Dadalaexpresini=&menestecadoel&mdebeleersecomoladireccindem C++incluyeunaformadepasarlosparmetrosporreferencia.Lasintaxisesint&iydebe serledocomolareferenciadelinti.Cambiosdeestosvaloresdentrolafuncinafectanel valordelosparmetrosalsalirdelamisma. Elpasajedeparmetrosporreferenciaesmseficienteyaquenonecesitarealizarlacopiade losvaloresenvariableslocalesalafuncin. Esposibledefinirfuncionesconelmismonombre(sobrecarga)siempreycuandotengan distintafirmaosignaturequesedefinecomolostiposycantidaddeargumentos. Unasugerenciaparacrearuntemplateescrearunafuncinparauntipodeterminadoy debugearlaparaasegurarsequehaceloquetienequehacer,yluegoanteponeraladefinicin delafuncintemplate<classT>yreemplazareltipoespecficoporT. Lasfuncionescontiposdeterminadostienenprioridadsobrelostemplates,loquehaceposible hacerfuncionesespecializadasquerequieranuncdigoespecialparadeterminadotipode parmetro,ydejareltemplateparaelresto. Esposibletambinutilizarsobrecargadefuncionesyalaveztemplates.Stringsseparadospor whitespcessonautomticamenteconcatenadosporelcompilador.
boolywchar_tsontiposnuevosquenoexistanenC. C++tambientieneeloperandosizeof()quedevuelvelacantidaddebytesqueocupaun determinadotipo. Enlalibrera"limits"deC++sedefineeltemplatenumeric_limits<T>quepermitesaberel valormximoquesepuedealmacenarenuntipo.Porejemplo"numeric_limits<double>::max()" Sesuguiereutilizarlostiposintydoublequesuelenserlosmseficientesencada implementacin. C++tienelaposibilidaddedefinirreferencias,identificadoresquesoncomosinnimosdeotros. Porejemploenlasiguientesdeclaracionsintnint&nn=nnynnapuntanalmismolugar, referencianelmismocontenido,peronosonexplcitamentepunteros.Estaeslabasedel pasajedeparmetrosporreferencia. Enlalibreraassertseencuentradefinidalafuncionvoidassert(expresion)Silaexpresion esfalsalaejecucinseparamostrandounerror.Paracancelarlosassertsedebedefinirla marcroNDEBUG.
Lamatrizdeconexionesesgeneralmentemejor(utilizamenosmemoriayresultaenalgoritmos mseficiente)engrafosdensos(conmuchosgradospornodo),perolamayoradelos problemasdelavidarealserepresentanengrafosnodensosoescasos(sparse). Suelenclasificarselosgrafoscomodirigidos,nodirigidosytambinpuedeindicarseunpeso(o costo)paracadauninentrevrtices.Enlosgrafosnodirigidos(undirectedgraph)losbordes (edges)notienenorientacin,adiferenciadelosgrafosdirigidos(directedgraph)formadospor paresordenadosindicandoelvrticedeorigenyeldedestino.Losgrafosdirigidospueden pensarsecomocaminosdeunasolamano,mientrasquelosnodirigidoscomorutasdedoble mano. ElalgoritmodecaminomscortodeDijkstraesparagrafosconpesosencadaarista(los cualesnopuedensernegativos)enelcualsedefineunnododeorigenyotrodedestino. Enestealgoritmosemantienendosconjuntos.Unconjuntocerrado(closedset)conlos caminosmscortosencontradoshastaelmomentoyotroconjuntoabierto(openset)con todoslosnodosquesepuedenalcanzar. SepuedeencontrarmsinformacinenestelinkdeWikipedia. Unadelasformasdedefinirtiposesconenum.Porejemplolasiguientesexpresindefineel tipocolor:typedefenumcolor{RED,WHITE,GREEN}color.Sibiensepuedendefinircomo constantesindependientes,enumtienelaventajadeagruparlascomosifueranuntipo extendido. Enestecasoenumcolor{RED,WHITE,GREEN}esuntipoycontypedefsedefineacolor comounsinnimodeesetipo.Sinousramostypedeflasiguienteexpresinenumcolor {RED,WHITE,GREEN}colordefineunavariablecolordeltipoenumcolor{RED,WHITE, GREEN}. Unodelossecretosdeunabuenaprogramacinorientadaaobjetosesdefinirtiposque parezcannativosenellenguaje. Lasobrecargadeoperadoressirveparaquelostipossecomportenmsnaturalmente.En ciertaformaescomodefinirunafuncin,ylasobrecargaesusadadependedelafirmadel operador(lacantidadytiposdeparmetrosusados). Unodelosoperadorestpicamentesobrecargadoes<<porejemplosegnelsiguientecdigo: ostream&operator<<(ostream&out,daysd){.returnout}dondeoperator<< representaraelequivalentealnombredelafuncin. EnCpodemosdefinirunpuntoconlasintaxistypedefstructpoint{doublex,y}point.En cambioenC++podemosdefinirunpuntoconlasintaxisclasspoint{public:doublex,y}y nonecesitamoselusodetypedefyaqueelnombredelaclaseesalavezelnombredeltipo. EnC++structesprcticamenteigualaclassdondetodoslosmiembrosymtodosson
f o r ( i n t j = 0 j < s i z e j + + ) { o p e n [ j ] = o p e n [ j ] | | g r a p h [ i ] [ j ] } i f ( c _ s i z e = = s i z e ) r e t u r n t r u e / / c o n n e c t e d i f ( o l d _ s i z e = = c _ s i z e ) r e t u r n f a l s e / / u n c o n n e c t e d } }
EnC++11enlugarde0est(olamacroNULLcomoconvensin)definidonullptrlocual permiteuncontrolmssegurosdetipos. Escomnagregarunconstructordecopia(copyconstructor).Siporejemplosiestuviramos definiendolaclaselist,lasintaxisdelconstructordecopiaseralist(constlist&lst) Esimportantediferenciarlacopiaprofundavscopiasuperficial(otambinllamadacopiade referencia).Elusodeunayotradependebsicamentesiloquesenecesitaesunacopia independientedelaoriginal,afindemodificaragustosucontenidoono.Elprimercaso requeriraunacopiaprofunda,lacualesmscostosaanivelderecursos. Enelcursoserecomiendausarelprogramavalgridparadetectarmemoryleaks. EnlalibreradetiposestndaroSTL,ungrupodeclasessonllamadoscontenedores,donde laclasevectoreslamsimportante.Enelcursoserecomiendafuertementeusarlaclase vectorenlugardearraybsicodeC,conelcualesmuchomsfacilcometererroresenel manejodendicesoreservadememoria. OtraclasedelaSTLeslist,lacualesdoblelinkedlacualsepuedenavegar bidireccionalmente. Elvectoresmstilcuandosetienequeaccederacualquierelementoalazar,ylistesms eficientecuandosenecesitaconstantementeestaragregandoyeliminandoelementos.
HaygrafosquenotienenMST,comoporejemploenelcasoqueunvrticeestdesconectado. Cualquieralgoritmodebetenerestasituacinencuenta,porejemplodevolviendounnmero negativo. ElalgoritmodeJarnikPrimcomienzaconunvrticeyrepetidamenteunelosbordesdemenor pesoqueconectanalrbol(desdecualquiervrticedelrbol)conunvrticequenopertenece alrbol(estaltimacondicingarantizanoseformenbucles).Acadapaso,elrbollqueseva formandoesunMSTentrelosvrticesquesevayanprocesando. Sienungrafohayformaquedesdeunvrticessellegueacualquierotrovrtice,entonceshay unST,ylaexistenciadeunST,implicaqueexisteunMST. Podramosllamarconjuntoabierto(openset)alosvrticesannoconectadosalrboly conjuntocerrado(closedset)alosquepertenecenalrbol.Laideadelalgoritmoesbuscarel vrticedelconjuntoabiertoqueestmscercadecualquieradelosnodosdelconjunto cerrado. Elconjuntoabiertosepuedeimplementarcomounalistaconprioridad,deformadeelegir siempreelvrticequetengaelmenorpesodeborde. Enelcasodequehayamsdeunbordeconelmismovalor,sepuedeelegircualquieradelos dos,yelcostodelosMSTvaaserelmismo,aunquelatopologadelrbolensseadistinta.Es decirelMSTnoesnico,perosielcostomnimo. ElpseudocodigodelalgoritmodePrimsepuedeencontrarenelsiguientelinkdewikipedia. ElalgoritmodeKruskalconsisteenordenartodoslosbordesposiblesdeungrafodemenora mayor,eirtomndolosaodescartndoloscuandoconformanunbucle.Elpseudocodigodel algoritmodeKruskalsepuedeencontrarenelsiguientelinkdeWikipedia. Sedefinecomoalgoritmocodiciosoovoraz(oGreedyAlgorithmentrelosqueseencuentran losalgoritmosdePrimyKruskal)esaquelque,pararesolverundeterminadoproblema,sigue unaheursticaconsistenteenelegirlaopcinptimaencadapasolocalconlaesperanzade llegaraunasolucingeneralptima.Enalgunoscasosestosalgoritmosnoencuentranla solucinptimadelproblema,peromuchasvecesselosemplea,porqueporsueficiencia encuentranunasolucinaceptable. Unodelosprincipiosdeprogramacinorientadaaobjetosesquelostiposdefinidosporel usuario,seanindistinguiblesdelostiposnativosdelidioma. Agregandoexplicitaladefinicindeunconstructor(odesdeC+11)aunoperadorde conversin,seimpidelaconversinimplcitadetiposounainicializacinporcopiayobligael usodestatic_cast.Porejemplodaraunerrorsihacemosa=bsiafueraunpuntoybun entero,aunsiexistieraunconstructordeltipopuntoquetuvieraunnicoenterocomo parmetroonlasintaxispoint::point(int){}
Porelcontrario,sihacemosb=a,esimposibledefinirunconstructordeconversinparaun tipoenteroquepermitaconvertirunpuntoenunentero.C++permitedefinirunoperadorde conversinconlasintaxispoint::operatorint(){...}loquepermitiraconvertirunpuntoaun int.Sinembargonoesrecomendadoanoserqueseasemnticamentenaturallaconversinde tipos(esdecirquetengaunsentidoclaro). Paraelegirlafuncinaejecutar,elcompiladorprimerobuscalafuncincuyafirmacohincida exactamenteconlosparmetrosusados,sinolaencuentrausalaspromocionesestandard (comodeintadouble).Luegousalasconversionesdetipoestandard(comoporejemplodeint ashort)ycomosiguientecriteriousalasconversionesdefinidasporelusuario. Lalibreradetemplatesestndar(oSTL)sebasaenContenedores,IteradoresyAlgoritmos. Lasclasesvector,list,set,dictymapsonejemplosdecontenedores.vectorylistsonloque llamamoscontenedoressecuenciales(loqueimplicaquesuselementossepuedenacceder conunndice).Porotrolado,porejemploaset,dictymapselosllamacontenedores asociativosylaformadeaccedergeneralmenteesconunaclavequenospermiteaccederal contenido. Loscontenedoressepuedenexpandiramedidaqueesnecesario. Lositeradoressonalgosimilarapunterosperogeneralizadosyconfuncionesestandarizadas. Haycuatrotipodeiteradores:forward,backward,randomyaccess.Unadelasventajasdelos iteradoresesquenopermitenleerelementosfueradelrangodelarray,queeseltpicoerrorque generaunerrorsegmentfault. Losalgoritmos(comoporejemplosortopermute)sepuedenaplicaramltiplesclases. PorejemplolaprogramacinconestilotpicodeC:
f o r ( i n t i = 0 i < 1 0 0 i + + ) { . . . }
esreemplazadaenelestilodeC++porelusodeiteradores:
f o r ( v e c t o r < i n t > : : i t e r a t o r p = v . b e g i n ( ) p ! = v . e n d p + + ) { . . . }
asuvezenC++11sesugierereemplazarpor:
f o r ( a u t o p = v . b e g i n ( ) p ! = v . e n d p + + ) { . . . }
Constuctores:
v e c t o r < T > v / / s e c u e n c i a v a c a . v e c t o r < T > v ( n ) / / c r e a u n v e c t o r c o n n e l e m e n t o s y l l a m a a l c o n s t r u c t o r T ( ) p a r a c a d a e l e m e n t o . v e c t o r < T > v ( n , v a l o r > / / V a l u e d e t i p o T o c o n v e r t i b l e a T y e l v a l o r q u e s e a s i g n a a c a d a e l e m e n t o .
Paramanipulararchivosusarlalibrerafstream.Porejemploifstreamifp("data",ios::in)crea lavariableifp(punteroaunarchivodeingresodedatos)parasulectura.Lavariableifptieneel mtodoeof() UnanuevafuncionalidaddeC++11eselforpararangos.Lasintaxises'for(declaracion: expresin){...}'.Porejemplofor(doubled:data)sum+=d Elrangoesimplcitodeprincipioafin. Dentrodelaexpresindeunforsepuedenusarunarray,uncontenedordesecuenciaoun string. Porejemplofor(auto&element:data)element=element+2//alponercomoreferenciase puedecambiarelvalordecadaelemento. Hay5categorasdeiteradores(demssimpleamscomplejo): input:Sololectura,unasolapasada.Permiterecorrerloselementosunoporunoydebetener eloperador++yeloperador*dedereferenciadefinidosyeloperador>.Lositeradorestambin debendefinidos==y!=.Porejemploeselrequerimientodelafuncin'find'unelementoenuna lista. output:Soloescritura,unasolapasada forward:Lecturayescritura,multipasadaenunasoladireccin.Untpicoalgoritmoqueusa estetipodeiteradoresreplace. bidirectional:Multipasadaenambasdirecciones.Esteiteradordebeimplementareloperador. Untpicoalgoritmoqueusaestetipodeiteradoresreverse. random:accedeacualquierelemento,esindexable.Estetipodeoperadorpermiteaccedera cualquierelementoenuntiempofijo.Necesitatenerdefinidoslosoperadoresdecomparacin pormayor,menoreigualdad.Generalmenteseimplementaconaritmticadedireccionesde memoria,comoloseraunarrayenC,conunadireccinbaseyunoffsetteniendoencuentael tamaoenbytesdecadaelemento.Untpicoalgoritmoqueusaestetipodeiteradoressort. Cuandosedesignaunalgoritmosedebepensarlaversinmseficientedelalgoritmoqueusa laversinmssimpledeiterador. Lalibrera'numeric'contienealgoritmoscomo'accumulate(input_it_begin,input_it_end,
start_value)'.Estealgoritmoutilizauniteradortipoinput.
Porejemploestaesunafuncinqueusaiteredoresdeltipoforwardyreemplazacadaelemento deuncontenedorporsucuadrado:
t e m p l a t e < t y p e n a m e F o r w a r d I t e r a t o r > v o i d s q u a r e ( F o r w a r d I t e r a t o r f i r s t , F o r w a r d I t e r a t o r l a s t ) { f o r ( f i r s t ! = l a s t f i r s t + + ) * f i r s t = ( * f i r s t ) * ( * f i r s t ) }
Eliteradorx.end()apuntamsalldelfinaldelcontenedor.Porlotantolosalgoritmosque necesitanaccederalltimoelementodelcontenedorcomienzandecrementandoelpuntero. Enlalibrera<cstddef>seencuentradefinidoeltipoptrdiff_telcualseutilizaparaalmacenar diferenciaentrepunterosenaritmticadedirecciones. EldiseodelaSTLestbasadoenlosprincipiosdeeficiencia(esunadelasrazonesdeserde C,cercadelmetalysacarelmayorjugoposiblealhardware),paramtrico(conelusode templates,lostipossonparmetrosypermiteutilizarelmismocdigobajodistintas necesidades)yortogonal(cubrirtodaslasnecesidadesdentrodelalcancedelalibrera). Unainterfaztpicadeuncontenedorincluye: Constructores(defaultconstructors,copyconstructors,moveconstructorsnuevoen C++11) Accesoaloselementos Insercindeelementos Emplacementdeelementos(nuevoenC++11) Borradodeelementos Destructures Iteradores Loscontenedorestambintienenlacapacidaddereservaryliberarmemoriaparalosobjetos quecontienen. Loscontenedoresasociativos,comoset,multiset,mapymultimapasocianunvaloraotroy sebasanenalgoritmosdeinsercinybsquedaquetrabajanconrbolesbalanceadosloque minimizaeltiempodebsqueda,peronecesitanqueloselementossepuedancomparar. ConC++11seintroducenloscontenedoresasociatiosunordered_mapyunordered_setque tienentiemposdebsquedaconstanteysebasanentablashash.Engeneralreemplazanlas versionesbasadasenrbolesbalanceadosespecialmentecuandonosenecesitaelconcepto deordenyencontenedoresconmuchoselementos. Loselementosdeloscontenedoresasociativossonpairyporlotantoelvalorclaveseobtiene
con(*p).firstyelvalorasociadocon(*p).second(siendopuniterador). LosalgoritmosdelalibreraSTLsebasanenloscontenedoreseiteradores.Soneficientesy utilizaneltipodeiteradorquefacilitaelalgoritmomseficiente. Losalgoritmossepuedencatalogarenalgoritmosdeordenamiento,algoritmosqueno modificanalcontenedor,algoritmosquecambianelcontenedoryalgoritmosnumricosque realizanclculosenbasealoselementosdelcontenedor. Elalgoritmostable_sort()garantizaqueloselementosconelmismovalormantienenlamisma posicinrelativadentrodelcontenedor. Lafuncintpicadeunalgoritmoquenocambialosvaloresdeloselementosdeuncontenedor esladebuscarunelementoydevolversuposicin. Envezdebuscaporunelementodeterminadoelalgoritmodebsquedapuedebuscarporun predicadootambinllamado"functor"quedevuelveTrueoFalsesisecumpleunacondicin. Elusode"functores"aumentalaortogonalidaddelalibrerapermitiendosuaplicacinamuchos mscasos. Unalgoritmomuyutilesfor_each()elcualejecutaunafuncinconloselementosdeun contenedor.Sifirmaes:
t e m p l a t e < c l a s s I n p u t I t e r , C l a s s F u n c t i o n > v o i d f o r _ e a c h ( I n p u t I t e r b , I n p u t I t e r e , F u n c t i o n f )
C++11introducelasfuncioneslambda,ofuncionessinnombre.for_each()sevemuy beneficiadaconlasfuncioneslambdaquesedefinendentrodelallamadaalafuncin. Enlasfuncioneslambda,sesuelenutilizarvariablesstaticpararetenervaloresentremltiples llamadasalafuncin.Porejemplo[](int&i){staticintn=1,i=n++}. Noesimprescindibledefinireltipoquedevuelveunafuncinlambdayaqueelcompiladorlo puedededucirdelaexpresintraselreturn.Sinembargoesposible[](intn)>int{returnn++}. copy()esunalgoritmoquemodificaelcontenedor. Elalgoritmoaccumulate()puederecibircomoparmetrounoperadorbinarioenelcasoes posibleusarunafuncionlambdacomo[](Ta,Tb){....} STLtambinusaobjetosfunciones,quesonclasesquetienendefinidoeloperator().Un ejemplodeusopodrasersum=accumulate(v1,v1*LENGTH,minus<int>())dondeminus esunaclaseconeloperador()definido. OtroconceptoqueseusajuntoconSTLsonlosobjetosgeneradorescomomuestrael siguientecdigo:
c l a s s g e n { p u b l i c : g e n ( d o u b l e x _ z e r o , d o u b l e i n c r e m e n t ) : x ( x _ z e r o ) , i n c r ( i n c r e m e n t ) { } d o u b l e o p e r a t o r ( ) ( ) { x + = i n c r r e t u r n x * x } p r i v a t e : d o u b l e x , i n c r } d o u b l e i n t e g r a t e ( g e n g , i n t n ) { v e c t o r < d o u b l e > f x ( n ) s t d : : g e n e r a t e ( f x . b e g i n ( ) , f x . e n d ( ) , g ) r e t u r n ( a c c u m u l a t e ( f x . b e g i n ( ) , f x . e n d ( ) , 0 . 0 ) / n ) } i n t m a i n ( ) { c o n s t i n t n = 1 0 0 0 g e n g ( 0 . 0 , 1 . 0 / n ) c o u t < < i n t e g r a t i o n p r o g r a m x * * 2 < < e n d l c o u t < < i n t e g r a t e ( g , n ) < < e n d l }
Elcomportamientodelalgoritmogenerate()delaSTLesequivalentea:
t e m p l a t e < c l a s s F o r w a r d I t e r a t o r , c l a s s G e n e r a t o r > v o i d g e n e r a t e ( F o r w a r d I t e r a t o r f i r s t , F o r w a r d I t e r a t o r l a s t , G e n e r a t o r g e n ) { w h i l e ( f i r s t ! = l a s t ) { * f i r s t = g e n ( ) + + f i r s t } }
queenestecasosumadosoperadoresdeltipoT. Elalgoritmotransform()aplicaunafuncinaloselementosdeuncontenedoryguardael
Elmecanismodelaherenciapermiteobtenernuevasclasesdeclasesexistentes(llamadas clasesbase). Tienecomoobjetivoreutilizarcdigoylasclasesobtenidassedesarrollandelaclasebase agregandonuevocdigoocdigoalternativo.Engenerarlasclasesheredadasagregan informacin. Lajerarquadetiposrelacionadospermitecompartircdigoeinterfaz. EnC++esposibledefinirsimpleomltipleherencia. Lasclasespermitendefinirunaclasificacintaxonmica,esdecirgruposdeclasesque compartenungrupodecaractersticas. Entrelasclasessepuedendefinirdistintostiposderelaciones.PorejemplounelefanteISA mamfero,ylaclasecircoHASAelefante. Unamtodovirtualesunmtodoqueesdeclaradoenlaclasebaseypuedeserreemplazado (overridden)enlaclasederivada.Estereemplazosediferenciadelasobrecargaenquepuede tenerlamismafirma.MedianteelpunterothisC++accedealafuncinadecuadaparacada claseentiempodeejecucinenformadinmica.Aestemecanismoselollamapolimorfismo puro. Paraqueestoseaposible,elobjetodebetenerinformacindetipoquepuedaserusada dinmicamente. Paraevitarlasobrecargaasociadaalastablasdebsquedadinmicaentiempodeejecucin debedefinirseunmtodocomonovirtual. Porejemplosidefinimosclasspoint3d:publicpoint{...}elconstructordelaclasepoint3d podraserpoint3d():point(),z(0.0){}elcualllamaalconstructordesuancestro. C++permiteimpedirquesepuedaheredardeunaclaseconlapalabraclavefinal.Porejemplo enladefinicinclasspoint3dfinal:publicpoint{...}laclasepoint3dnosepudeutilizarpara derivarunanuevaclase. ElconceptodepuentesesunaestrategiamuyusadaenHexyrecomiendaincorporarcomo partedelprograma. Paraidentificarunnodo(i,j)sepuedeutilizarlafrmulan=i*lado+jdndeladoeslalongitud deceldasporladodeltablero.Deestaformasepuedepasardelarepresentacin bidimensionaldeltableroaunalinealdenodos.Parapasardelnmerodeno=doala representacinbidireccionalsepuedeusarladivisinyelmdulodeenterosi=n/ladoj=n %ladoEnamboscasosi,jyncomienzanen0. UnejemplodelaclasehexGraphpodraser:
Porejemplo,paranodosinternoslasconexionesson:
e l s e { e l i s t . p u s h _ f r o n t ( i * 1 1 + j + 1 ) e l i s t . p u s h _ f r o n t ( i * 1 1 + j 1 ) e l i s t . p u s h _ f r o n t ( ( i + 1 ) * 1 1 + j ) e l i s t . p u s h _ f r o n t ( ( i + 1 ) * 1 1 + j + 1 ) e l i s t . p u s h _ f r o n t ( ( i 1 ) * 1 1 + j ) e l i s t . p u s h _ f r o n t ( ( i 1 ) * 1 1 + j 1 ) }
Laexpresinvoidprint()constindicaqueelpunterothisnoseverafectadodentrodel miembroprint(). Serecomiendautilizarprotectedenlugardeprivateparadefinirmiembrosdeunaclase,ya quesinousaesaclaseparacrearsubclases,elencapsulamientoselograigual,perodejala puertaabiertaacrearsubclases. GradyBoochescribivariasreglasdebuenasprcticasdeOOP.Unadeellasindicaquees convenienteentenderlosobjetosenelmundorealantesdecrearelprograma,ymuchasveces elprogramadordebetrabajarconunespecialistaeneldominioparaelcualseaplicael programa. Punterosdeltipodelaclasebasepuedenserutilizadosparaapuntarobjetosdelassubclases. Silaclasegrad_studentheredadestudent,entoncessepuedereemplazarelmtodoprint()de studentengrad_studentconestasintaxis:
v o i d g a d _ s t u d e n t : : p r i n t ( ) { s t u d e n t : : p r i n t ( ) c o u t < < n e w s t a f f }
Esimportantedestacarelusodeoperador::parapoderllamaralmiembrodelaclasebase.
Cuandolosmtodosnosonvirtuales,cadallamadoaprint(),dependiendodeltipodelpuntero, imprimelainformacindistinta,limitadaasutipo.Esteeselcomportamientopordefault.
s t u d e n t s ( ) , * p s = & s g r a d _ s t u d e n t g s ( ) , * p g s p s > p r i n t ( ) / / s t u d e n t : : p r i n t p s = p g s = & g s p s > p r i n t ( ) / / s t u d e n t : : p r i n t p g s > p r i n t ( ) / / g r a d _ s t u d e n t : : p r i n t
Elpunteropspuedeapuntaraobjetosdeltipostudentygrad_student,peroelpunteropgs solopuedeapuntaraobjetosdeltipograd_student. Conelusodevirtual,elcomportamientonodependedeltipodelpuntero(comoenelejemplo anterior)sinoaltipodelobjetoqueapunta. Elusodevirtualhacequeelcompiladornopuedadefinirdeantemanoquemiembrollamar,sino quecreaunatabladepunterosafuncionesqueesusadaentiempodeejecucin.Entiempode ejecucinelprogramaverificaaquetipodeobjetoestapuntando(informacinqueseguarda juntoconelobjeto)yejecutalafuncinadecuadaparaesetipo. Estoagregaungastoadicionalalllamadodelafuncin,yporesoenC++noesel comportamientopordefaultyrequiereelusodevirtual. Unavezqueseutilizaladecoracinvirtualparadefinirunmiembro,esacaractersticapersiste, ynoesnecesarioutilizarvirtualenlassubclases. Elsiguientecdigoejemplificaelcomportamientodevirtual:
c l a s s B { p u b l i c : i n t i v i r t u a l v o i d p r i n t _ i ( ) c o n s t { c o u t < < i < < i n s i d e B < < e n d l } } c l a s s D : p u b l i c B { p u b l i c : v o i d p r i n t _ i ( ) c o n s t { c o u t < < i < < i n s i d e D < < e n d l } / / v i t u a l } m a i n ( ) { B b , p b = & b D f f . i = 1 + ( b . i = 1 ) p b > p r i n t _ i ( ) / / c a l l B : : p r i n t _ i ( ) p b = & f p b > p r i n t _ i ( ) / / c a l l D : : p r i n t : i ( ) }
e x p l i c i t m y _ c o n t a i n e r ( T * b ) : m y _ c o n t a i n e r ( ) { f o r ( i n t i = 0 i < n i + + ) a [ i ] = b [ i ] }
/ / b d e j a d e s e r u n p u n t e r o v l i d o .
Elusodedeloperadormove()luegodel=indicaquesedeseautilizareloperador=conla firmade&¶moverynocopiar. Ladefiniciondemoveesstd:move()static_cast<T&&>(t) Esconvenienteparaejercitaragregareloperador[](index)alaclaseyimplementarlalgicade iteradores. Vislumbrarelfuturo(lookahead)esmuyusadoenAIdejuegos.Avecessepuedellegaralfinal deljuego,enotrashastallegaraunaposicinprometedora. EstavisinafuturosepuedeimplementarconelalgoritmoMinmax.Laideadelalgoritmoes elegirlajugadaquehagamenosposiblequeeloponenteminimicenuestropuntajeconsu prximajugada,yasenadelante.SeaplicaajuegosconinformacinperfectayMinimaxesun algoritmorecursivo. Estealgoritmosedebellamarcadavezquelacomputadoradebehacerunajugada.A continuacinunejemplo:
[ 6 ] M A X / | \ [ 1 ] [ 6 ] [ 3 ] M I N / \ | / | \ [ 5 ] 1 [ 6 ] 7 [ 3 ] [ 9 ] M A X / \ / | | | 2 5 6 1 3 9 M I N
EnlajergasedefinePlyacadapasoenlaprofundidadtotaldelrbolyBranchingrateala cantidaddenodosquecuelgandecadanodo. PararecortarelrbolesbuenodefinirunalgoritmoquegenereloquesellamaPlausibleMove, quesonlasjugadasmsprometedoras. EnHexestealgoritmopodraanalizar: Sisepuedengenerarjugadasganadoras. Sisepuedebloquearoprevenirqueeloponentegane. Siesposibleextenderelcaminomslargo. Siesposiblebloquearelcaminomslargodeloponente. Siesposibleextenderohacerunpuenteparauncamino. Siesposibletomarunadelascasillascentrales Sisepuedemoverhaciaunacolumna(ofila)annoocupada TodaalgoritmodeIArequierelaposibilidaddeevaluarunaposicinestticaparacomparary elegirunajugadaenlugardeotra.EnHex,quienestmscercadehaceruncaminocompleto deextremoaextremo,esunaformarpidaderealizarestaevaluacin. AlfaBetaesunaevolucindeMinmax.Elalgoritmopodalasramasquenoinfluyenenla decisindelalgoritmosMinmax. Lapodaalfabetatomadichonombredelautilizacindedosparmetrosquedescribenlos lmitessobrelosvaloreshaciaatrsqueaparecenalolargodecadacamino. eselvalordelamejoropcinhastaelmomentoalolargodelcaminoparaMAX,esto implicarporlotantolaeleccindelvalormsalto.sesueleinicializareninfinito. eselvalordelamejoropcinhastaelmomentoalolargodelcaminoparaMIN,esto implicarporlotantolaeleccindelvalormsbajo.sesueleinicializaren+infinito. Estabsquedaalfabetavaactualizandoelvalordelosparmetrossegnserecorreelrbol.El mtodorealizarlapodadelasramasrestantescuandoelvaloractualqueseestexaminando seapeorqueelvaloractualdeoparaMAXoMIN,respectivamente.
[ 5 ] M A X
/ | \ [ 5 ] [ 3 * ] [ 4 * ] M I N / | / | \ | \ [ 5 ] [ 7 * ] [ 8 ] [ 3 ] [ * ] [ 4 ] [ * ] M A X
/|/|\/|||\|\/|\ 457388439534547 ******* Unavezqueencuentraelmaximizadorencuentrael7*,sabequealminimizadordeorden superiorledejadeinteresartodalarama,porqueaunqueencuentreunvalormenorlmismo(el maximizador)lovaadescartar. Lomismopasacuandoelminimizadorencuentrael3*,sabequealmaximizadordeorden superiorledejadeinteresartodalarama,porqueaunqueencuentreunvalormayorlmismo(el minimizador)lovaadescartar. Laejecucindeunaexpresinmatemticaselapuedevercomounrbol,dondelashojasson losvaloresylosnodosinternoslasoperacionesmatemticas.Sepuedeexpresarcon parntesisoennotacinpolacainversa. Elrecolectordebasuraporreferenciaesunalgoritmoquellevalacuentadecuantospunteros hacenreferenciaaunobjeto,ynoloborranhastaqueesacuentallegueacero.
c l a s s N o d e { f r i e n d c l a s s T r e e f r i e n d o s t r e a m & o p e r a t o r < < ( o s t r e a m & , c o n s t T r e e & ) i n t u s e / / r e f e r e n c e c o u n t G C p r o t e c t e d : N o d e ( ) { u s e = 1 } v i r t u a l v o i d p r i n t ( o s t r e a m & ) = 0 / / p u r e v i r t u a l v i r t u a l ~ N o d e ( ) { } / / n o t e v i r t u a l d e s c t r u c t o r v i r t u a l v o i d p r i n t ( o s t r e a m & o ) = 0 / / p u r e v i r t u a l v i r t u a l i n t e v a l ( ) = 0 / / p u r e v i r t u a l } c l a s s T r e e { f r i e n d c l a s s N o d e / / o k a y b e t w e e n c o u s i n f r i e n d o s t r e a m & o p e r a t o r < < ( o s t r e a m & , c o n s t T r e e & ) N o d e * p / / p o l y m o r p h i c h i e r a r c h y p u b l i c : T r e e ( i n t ) / / c o n s t a n t T r e e ( c h a r ) / / v a r i a b l e T r e e ( c h a r * , T r e e ) / / u n a r y o p e r a t o r T r e e ( c h a r * , T r e e , T r e e ) / / b i n a r y o p e r a t o r T r e e ( c o n s t T r e e & t ) { p = t . p + + p > u s e } / / r e f e r e n t i a l c o p y c o n s t r u c t o r ~ T r e e ( ) { i f ( p > u s e = = 0 ) d e l e t e p } v o i d o p e r a t o r = ( c o n s t T r e e & t ) i n t e v a l ( ) { r e t u r n p > e v a l ( ) } } o s t r e a m & o p e r a t o r < < ( o s t r e a m & o , c o n s t T r e e & t )
{ t . p > p r i n t ( o ) r e t u r n ( o ) } c l a s s L e f t N o d e : p u b l i c N o d e { f r i e n d c l a s s T r e e v i r t u a l v o i d p r i n t ( o s t r e a m & o ) = 0 / / p u r e v i r t u a l v i r t u a l i n t e v a l ( ) = 0 / / p u r e v i r t u a l }
Elprimerejemploesparaunaconstante,yelsegundoparaunavariablerepresentadaporun caracteryalmacenadaenunarraydeint.
c l a s s U n a r y N o d e : p u b l i c N o d e { f r i e n d c l a s s T r e e c h a r * o p T r e e o p n d U n a r y N o d e ( c h a r * a , T r e e b ) : o p ( a ) , o p n d ( b ) { } v o i d p r i n t ( o s t r e a m & o ) { o < < ( < < o p < < o p n d < < ) } p u b l i c : i n t e v a l ( )
} i n t U n a r y N o d e : : e v a l ( ) { s w i t c h ( o p [ 0 ] { c a s e : r e t u r n ( o p n d . e v a l ( ) ) c a s e + : r e t u r n ( + o p n d . e v a l ( ) ) d e f a u l t : e r r < < n o o p e r a n d \ n < < e n d l r e t u r n 0 } } c l a s s B i n a r y N o d e : p u b l i c N o d e { f r i e n d c l a s s T r e e c h a r * o p T r e e l e f t T r e e r i g h t B i n a r y N o d e ( c h a r * a , T r e e b , T r e e c ) : o p ( a ) , l e f t ( b ) , r i g h t ( c ) { } v o i d p r i n t ( o s t r e a m & o ) { o < < ( < < l e f t < < o p < < r i g h t < < ) } p u b l i c : i n t e v a l ( ) } i n t B i n a r y N o d e : : e v a l ( ) { s w i t c h ( o p [ 0 ] { c a s e : r e t u r n ( l e f t . e v a l ( ) r i g h t . e v a l ( ) ) c a s e + : r e t u r n ( l e f t . e v a l ( ) + r i g h t . e v a l ( ) ) c a s e * : r e t u r n ( l e f t . e v a l ( ) * r i g h t . e v a l ( ) ) d e f a u l t : e r r < < n o o p e r a n d \ n < < e n d l r e t u r n 0 } }
Conestaformadeprogramarselogracdigofcilmenteextensible. AcontinuacinsemuestranlosconstructoresdelaclaseTree:
T r e e : : T r e e ( i n t n ) { p = n e w I n t N o d e ( n ) } T r e e : : T r e e ( c h a r i d ) { p = n e w I d N o d e ( i d ) } T r e e : : T r e e ( c h a r * o p , T r e e t ) { p = n e w U n a r y N o d e ( o p , t ) } T r e e : : T r e e ( c h a r * o p , T r e e l e f t , T r e e r i g h t ) { p = n e w B i n a r y N o d e ( o p , l e f t , r i g h t ) }
Lasintaxisdecatchescatch(sometype).Elvalores...esespecialysignificaquecualquier excepcinsercapturada.
Paracompilarengccsedebeusarlaopcinpthread. Esimportantehacerverificacionesqueellasobrecargadelusodethreadjustifiquelasoluciny resulteenunprogramamseficiente. Lalibrera<tuple>defineeltemplatetuple<listadetipos>quepermiteasociarunapequea cantidaddeelementosdecualquiertipo. Porejemplo,sidefinimoslavariablepcomotuple<int,double,int>,paraasociarunnuevo tuplealavariablepodramosusarelcdigop=make_tuple(1,1.5,2)yparaobtenerlos valoresindependientessedebeusarget<0>(p)get<1>(p)yget<2>(p) Tupleayudaalaprogramacinbasadaengenricos. AcontinuacinunresumendedistintasfuncionalidadesdeC++11(lasnuevasestnresaltadas ennegrita).
# i n c l u d e < i o s t r e a m > # i n c l u d e < s t r i n g > u s i n g n a m e s p a c e s t d c l a s s s i m p l e { p u b l i c : s i m p l e ( ) = d e f a u l t / / c o m p i l e r g e n e r a t e d c o n s t r u c t o r s i m p l e ( d o u b l e x ) = d e l e t e / / s u p p r e s s e d c o n v e r s i o n c o n s t r u c t o r / / i m p i d e q u e e s a f i r m a s e a v l i d a s i m p l e ( i n t x , i n t y ) : p ( x ) , q ( y ) { } s i m p l e ( i n t x ) : s i m p l e ( x , 1 ) { } / / d e l e g a t e c o n s t r u c t o r s i m p l e ( c o n s t s i m p l e & x ) : s i m p l e ( x . p , x . p ) { } / / c o p y c o n s t r u c t o r s i m p l e ( s i m p l e & & x ) : s i m p l e ( x . p , x . p ) { x . p = x . p = 0 } / / m o v e s e m a n t i c s p r i v a t e : i n t p = 0 , q = 1 / / d e f a u l t i n i t i a l i z e r c a n b e o v e r r i d d e n } c l a s s r a t i o n a l : p u b l i c s i m p l e { p u b l i c u s i n g s i m p l e : : s i m p l e / / i m p l i c i t l y d e c l a r e s c o n s t r u c t o r s b u t u s e b a s e . / / i m p o r t a l o s c o n s t r u c t o r e s d e l a c l a s e b a s e . }