Kodestil i C++ Simen Hagen 26.9.2003 Introduksjon I store programmeringsprosjekter er det viktig at koden har et konsistent utseende og at alle bruker en felles stil på koden. Alle som skriver kode har sin egen stil, og for å unngå at det blir en merkelig blanding av mange forskjellige stiler er det viktig å ha noen regler som alle utviklerene følger. Selv for mindre prosjekter er det mange fordeler ved å ha en programmeringsstil som er enkel å lese og lett og få oversikt med. Som ny til språket C++ er det ikke så lett å vite hva som er gode og hva som er dårlige vaner. For å hjelpe deg med å nne ut av det vil dette dokumentet presentere en standard. Om du ønsker å bruke den er selvsagt opp til deg, men å nne en standard som du liker, og så holde seg til den, er viktig. Eksprimenter med forskjellige metoder og nn en du liker selv. Tenk igjennom hvorfor du liker akkurat den metoden du har funnet. Lytt til hva andre sier, og hvorfor de liker sine standarder. Plukk det beste fra de stedene som er tilgjengelige. Navnekonvensjoner Det bør være selvforklarende hva alle variablene er. Velg navn som er lett å forstå. Det er mye bedre å bruke et langt navn som bestå av ere ord, enn å forkorte det for mye. En variable med navn 'dette_er_et_langt_navn' er bedre enn 'deeln'. Det første navnet er enkelt å forstå, men det andre gir ikke mening hvis du ikke på forhånd vet hva det skal bety. Globale variabler Alle globale variabler burde starte med '//'. Globale variabler er en vanlig kilde til feil, og bør unngås hvis mulig. Nå er det ikke alltid det er mulig å unngå det, eller at det av forskjellige grunner er mer praktisk å bruke en global variabel. Om så er tilfelle, bruk prekset 'GLOBAL\_'. På den måten unngår en at de globale navnene kollidere med lokale navn, og det er lett å se om variabelen er global eller ikke. Det er også lurt å prøve å gi variablene navn som ikke er for generelle eller navn/ord som lett kan missforstås (f.eks. at de kan ha ere 1
meninger). En måte å unngå å bruke globale variabler på, er å bruke static klassevariabler i klasser. En annen mulighet er å legge alle globale variabler i et eget namespace. Klassevariabler og lokale variabler Fordi klassevariabler har et mer begrenset scope, er det ikke fullt så viktigå gi dem entydige navn som med globale variabler. Det er likevel viktig å gi gode navn. Eksempler på hvordan en kan navgi klassevariabler er 'min_variabel', 'minvariable', 'MinVariabel', 'Min_Variabel', eller varianter av dette. Lokale varibler kan kun sees fra den funksjonene de er i bruk, og har således et veldig begrenset scope. Viktigheten av å ha et unikt navn er derfor ikke så stor. Bruk gjerne samme regel som for klassevariabler. #dene og enum Det er vanligvis foretrukket å bruke 'enum' fremfor å bruke '#define', siden den første kan brukes som en datatype. En 'enum' kan brukes om en variabel, og vil derfor følge de samme regler som vanlige variabelnavn. Det er også mulig å bruke 'enum' i steden for '#define', og hvis det er tilfelle bør en bruke store brukes på samme måte som med '#define'. Det er ikke alltid det er praktisk å følge disse reglene, så det er lov å bruke litt skjønn. Funksjoner Funksjoner bør skrive med små bokstaver. Om navnet består av ere ord, bør ordene skilles med en '_', slik som f.eks. 'finn_neste'. Aksessfunksjoner Aksessfunksjoner (som blir brukt til å sette eller lese verdier til klassevariabler) bør hete det samme som variablen de skal aksessere, med en 'get_' eller 'set_' preks for det som passer. Globale funksjoner Globale funksjoner (funksjoner som ikke tilhører noen klasse) følger de samme reglene som andre funksjonsnavn. De bør altså skrives med små bokstaver og ha en '_' mellom ordne, f.eks. 'min_funksjon'. 2
Klasser Klassenavn bør være mulig å skille fra variabler og funksjoner bare ved å se på navnet. De kan skrives med stor bokstav først i hvert av ordene, og ordene skilles med en '_', f.eks. 'Min_Klasse'. Indentering All kode bør indenteres etter vanlige regler. Disse reglene er denert nedenfor. Det er anbefalt å sette tab størrelsen til 8, og indenterinsstørrelsen til 2. Det er også anbefalt å bytte ut alle tab tegn med mellomrom (de este editorer har en opsjon for dette). Utrykk For alle uttrykk gjelder følgende regler: Komma skal etterfølges av mellomrom, men det skal ikke være noe mellomrom før komma. Det skal være mellomrom både før og etter følgende operatorer: =, <, >,!=, og kombinasjoner av disse. Generellt skal det være mellomrom både før og etter disse operatorene: +, -, *, /. Det skal være et mellomrom før en startparentes '(' i et statement, men ikke etter. Påfølgende parenteser skal ikke være fulgt av mellomrom. For eksempel: if ((i+2)). Klasser Følgende regler gjelder klasser: Klassedenisjonen skal plasseres i en headerl (.h l). Nøkkelordet 'class' skal være plassert i venstre kolonne (kolonne 1), fulgt av navnet på klassen. Den første krøllparentesen ('{') skal plasseres på en egen linje, direkte under nøkkelordet 'class', i kolonne 1. Den avsluttende krøllparentesen ('') skal også stå på en engen linje i kolonne 1. For 'template' klasser skal nøkkelordet 'template' stå på en egen linje over nøkellordet 'class', fulgt av templateparameterene. Hvis klassen er en derivert fra en base-klasse skal kolonet (':') som følges av arveuttrykket plasseres på en egen linje, indentert et hakk til høyre, rett under klasseutrykket. 3
Det følgende er et eksempel på hvordan en derivert template klasse skal se ut: template <class T> class My_Class : public Base_Class { ; if-utrykk Et 'if'-utrykk bør skrives på en av følgende måte: if () { else { Løkker Alle løkker ('while, 'for' og 'do') bør skrives på følgende måte: while () { Kommentarer All kode bør dokumenteres. Det bør være nok kommentarer til at en leser som ikke kjenner koden skal kunne forstå hva som skjer, samtidig som det ikke skal være ere kommentarer enn at koden fortsatt er leselig. Hvis det er for mange kommentarer drukner koden i all den unødvendige teksten. Det er også viktig å gi korte men forståelige kommentarer. De skal være minimale, men tilstrekkelige. Hvis du lager klasser som skal brukes av andre er det spesiellt viktig å kommentere de delene som er del av det åpne grensesnittet. Virtual og static funksjoner Hvis en funksjon er virtual eller static, bør dette indikeres i kildelen (source len) ved skrive '/* virtual */' eller '/* static */' som en kommentar rett før funksjondeklaresjonen. Nedenfor er et eksempel på en virtual funksjon (og hvor du bare kan bytte ut 'virtual' med 'static' der hvor det passer): 4
/* virtual */ Return_Type* My_Class::do_something(const Some_Type variable) { 5