Lär dig mer om grundläggande datatyper

Slutförd

Go är ett starkt skrivet språk. Varje variabel som du deklarerar är bunden till en specifik datatyp och accepterar endast värden som matchar den typen.

I Go har du fyra kategorier av datatyper:

  • Grundläggande typer: tal, strängar och booleska värden
  • Mängdtyper: matriser och structs
  • Referenstyper: pekare, sektorer, kartor, funktioner och kanaler
  • Gränssnittstyper: gränssnitt

I den här modulen täcker vi bara de grundläggande typerna. Oroa dig inte om du inte vet vilka de andra typerna är. Vi går igenom dem i de kommande modulerna.

Vi börjar med att utforska de numeriska datatyperna.

Heltalsnummer

I allmänna termer är intnyckelordet för att definiera en heltalstyp . Men Go tillhandahåller också typerna int8, int16, int32och int64 som är ints med storleken 8, 16, 32 respektive 64 bitar. När du använder ett 32-bitars operativsystem är storleken vanligtvis 32 bitar om du bara använder int. På 64-bitarssystem int är storleken vanligtvis 64 bitar. Men det här beteendet kan skilja sig från en dator till en annan. Du kan använda uint. Men använd bara den här typen om du behöver representera ett värde som ett osignerat tal av en viss anledning. Go tillhandahåller uint8också typerna , uint16, uint32och uint64 .

Här är ett exempel på hur du använder de olika heltalstyperna i Go:

var integer8 int8 = 127
var integer16 int16 = 32767
var integer32 int32 = 2147483647
var integer64 int64 = 9223372036854775807
fmt.Println(integer8, integer16, integer32, integer64)

För det mesta använder intdu , men du behöver veta om de andra heltalstyperna eftersom i Go int inte är samma som int32, även om heltalets naturliga storlek är 32 bitar. Med andra ord måste du gjuta explicit när en rollbesättning krävs. Och om du försöker utföra en matematisk åtgärd mellan olika typer får du ett fel. Anta till exempel att du har den här koden:

var integer16 int16 = 127
var integer32 int32 = 32767
fmt.Println(integer16 + integer32)

När du kör programmet får du följande fel:

invalid operation: integer16 + integer32 (mismatched types int16 and int32)

Som du ser måste du uttryckligen ange den nya typen när du konverterar ett värde från en typ till en annan i Go. Vi ska prata om hur du castar typer korrekt i slutet av den här modulen.

När du går vidare med go-inlärningen kanske du hör talas om runs. A rune är helt enkelt ett alias för int32 datatypen. Det används för att representera ett Unicode-tecken (eller en Unicode-kodpunkt). Anta till exempel att du har följande kod:

rune := 'G'
fmt.Println(rune)

Du kan förvänta dig att programmet skrivs ut G i kommandotolken när du kör kodfragmentet ovan. Men du ser talet 71, som representerar Unicode-tecknet för G. Vi pratar mer om runor i de kommande modulerna.

Du kan lära dig mer om intervallen för varje typ genom att titta på Go-källkoden. Att känna till intervallen för varje typ hjälper dig att välja rätt datatyp, och du undviker också att slösa bort bitar i minnet.

Utmaning 1

Ange en annan variabel av typen int och använd värdet från variabeln integer32 eller integer64 för att bekräfta variabelns naturliga storlek på systemet. Om du använder ett 32-bitarssystem och använder ett värde som är högre än 2 147 483 647 får du ett spillfel som ser ut så här: constant 9223372036854775807 overflows int.

Utmaningslösning:

package main

import "fmt"

func main() {
   var integer32 int = 2147483648
   fmt.Println(integer32)
}

Utmaning 2

Deklarera en osignerad variabel som uintoch initiera den med ett negativt värde som -10. När du försöker köra programmet bör du få ett felmeddelande som det här: constant -10 overflows uint.

Utmaningslösning:

package main

import "fmt"

func main() {
   var integer uint = -10
   fmt.Println(integer)
}

Flyttalsnummer

Go tillhandahåller datatyper för två storlekar av flyttalsnummer: float32 och float64. Du kan använda dessa typer när du behöver lagra stora tal och de inte får plats i någon av de tidigare nämnda heltalstyperna. Skillnaden mellan dessa två typer är den maximala storleken på bitar som de kan innehålla. Titta på följande rader för att lära dig hur du använder dessa två typer:

var float32 float32 = 2147483647
var float64 float64 = 9223372036854775807
fmt.Println(float32, float64)

Du hittar gränserna för dessa två typer med hjälp math.MaxFloat32 av konstanterna och math.MaxFloat64 som är tillgängliga i math paketet. Använd följande kod för att skriva ut de högsta flyttalsvärdena i kommandotolken:

package main

import (
    "fmt"
    "math"
)    

func main() {
    fmt.Println(math.MaxFloat32, math.MaxFloat64)
}

Flyttalstyper är också användbara när du behöver använda decimaltal. Du kan till exempel skriva något som liknar den här koden:

const e = 2.71828
const Avogadro = 6.02214129e23
const Planck = 6.62606957e-34

Observera att Med föregående kod härleder Go datatyperna från de värden som används.

Booleska värden

En boolesk typ har bara två möjliga värden: true och false. Du deklarerar en boolesk typ med hjälp av nyckelordet bool. Go skiljer sig från andra programmeringsspråk. I Go kan du inte implicit konvertera en boolesk typ till antingen 0 eller 1. Du måste göra det explicit.

Så du kan deklarera en boolesk variabel som den här:

var featureFlag bool = true

Vi använder booleska datatyper i den kommande modulen när vi pratar om kontrollflödesinstruktioner i Go. Vi använder dem också i senare moduler.

Strängar

Slutligen ska vi titta på den vanligaste datatypen i alla programmeringsspråk: sträng. I Go används nyckelordet string för att representera en strängdatatyp. Om du vill initiera en strängvariabel måste du definiera dess värde inom dubbla citattecken ("). Enkla citattecken (') används för enkla tecken (och för runor, som vi såg i ett tidigare avsnitt).

Följande kod visar till exempel två sätt att deklarera och initiera en strängvariabel:

var firstName string = "John"
lastName := "Doe"
fmt.Println(firstName, lastName)

Ibland måste du fly från tecken. Om du vill göra det i Go använder du ett omvänt snedstreck (\) före tecknet. Här är till exempel de vanligaste exemplen på att använda escape-tecken:

  • \n för nya rader
  • \r för vagnreturer
  • \t för flikar
  • \' för enkla citattecken
  • \" för dubbla citattecken
  • \\ för omvänt snedstreck

Använd följande kodfragment för att testa escape-tecken:

fullName := "John Doe \t(alias \"Foo\")\n"
fmt.Println(fullName)

Du bör se följande utdata (inklusive den nya raden):

John Doe        (alias "Foo")

Standardvärden

Hittills, nästan varje gång vi har deklarerat en variabel, har vi initierat den med ett värde. Men i Go, till skillnad från i andra programmeringsspråk, har alla datatyper ett standardvärde när du inte initierar en variabel. Den här funktionen är praktisk eftersom du inte behöver kontrollera om en variabel har initierats innan du använder den.

Här är en lista över några standardvärden för de typer som vi har utforskat hittills:

  • 0 för int typer (och alla dess undertyper, till exempel int64)
  • +0.000000e+000 för float32 och float64 typer
  • false för bool typer
  • Ett tomt värde för string typer

Kör följande kodfragment för att bekräfta standardvärdena som angavs tidigare:

var defaultInt int
var defaultFloat32 float32
var defaultFloat64 float64
var defaultBool bool
var defaultString string
fmt.Println(defaultInt, defaultFloat32, defaultFloat64, defaultBool, defaultString)

Du kan använda kod som den här koden för att fastställa standardvärdet för en datatyp som vi inte utforskade här.

Typkonverteringar

I ett tidigare avsnitt bekräftade vi att implicit gjutning inte fungerar i Go. I Go måste gjutning göras explicit. Go erbjuder några inbyggda sätt att konvertera en datatyp till en annan datatyp. Ett sätt är till exempel att använda den inbyggda funktionen för varje typ, så här:

var integer16 int16 = 127
var integer32 int32 = 32767
fmt.Println(int32(integer16) + integer32)

En annan metod för gjutning i Go är att använda strconv-paketet. Om du till exempel vill konvertera en string till en int, och vice versa kan du använda den här koden:

package main

import (
    "fmt"
    "strconv"
)

func main() {
    i, _ := strconv.Atoi("-42")
    s := strconv.Itoa(-42)
    fmt.Println(i, s)
}

Kör föregående kod och bekräfta att den körs och skrivs -42 ut två gånger.

Observera att det finns ett understreck (_) som används som namn på en variabel i föregående kod. I Go _ innebär det att vi inte kommer att använda variabelns värde och att vi vill ignorera det. Annars kompileras inte programmet eftersom vi måste använda alla variabler som vi deklarerar. Vi återkommer till det här ämnet och du får lära dig vad som _ vanligtvis representerar i de kommande modulerna.