Declaring Variables

How var declares a variable with a type, with a value, or with both, and when Go works the type out for you.

Syntaxvar name Type = value // leave out the Type or the value, but not both

A variable is a name for a value. The name lets you use that value further down, and change it later. Go creates one with the keyword var.

The three shapes

  • var count int gives a type and no value. Go fills in that type's zero value, which for int is 0.
  • var count int = 7 gives both the type and the value.
  • var count = 7 gives only the value. The compiler works the type out from it. That is called inference.

You may leave out the type or the value. You may not leave out both, because then nothing says what the variable is.

What inference picks

Inference uses the value's default type. A whole number such as 7 gives int. A number with a decimal point gives float64. Text in double quotes gives string. true and false give bool. When you need a different type, write it down: var size int64 = 7.

Where a var can go

A var written outside every function, at the top level of a file, is a package-level variable. Every function in that package can read and change it. A var written inside a function belongs to that function and disappears when the function ends. Several declarations can be grouped under one var keyword in parentheses, which is how most packages list their top-level variables.

What trips people up

Declaring a variable inside a function and never using it is a compile error, not a warning. The program will not build. Either use the value or delete the line.

Example

Example · go
package main

import "fmt"

// A package-level variable sits outside every function.
var siteName = "soundscode"

func main() {
	// Type given, no value: count starts at the zero value for int, which is 0.
	var count int

	// Type and value both given.
	var price float64 = 9.99

	// Value only: the compiler infers the type string from "hello".
	var greeting = "hello"

	// One var keyword can declare a whole group.
	var (
		width  = 3
		height = 4
	)

	// No var keyword here. This is assignment to a variable that already exists.
	count = width * height

	fmt.Println(siteName, greeting, price)
	fmt.Println("count:", count)
}

// Output:
// soundscode hello 9.99
// count: 12

When to use it

  • Holding a running count or total that a function updates as it works.
  • Setting a package-level default, such as a service name, in exactly one place.
  • Declaring a value as int64 because the library you are about to call requires that type.
  • Listing all of a package's configurable variables in one grouped var block.

More examples

Choosing the type instead of letting Go choose

Libraries often demand an exact type, for example int64 for a byte count or float32 for graphics data. Writing the type in the declaration is how you get it. Reach for this whenever the value will be passed to something that insists on a particular numeric type.

Example · go
// Inference gives these the default types int and float64.
var count = 7
var ratio = 1.5

// When a specific type is needed, name it. Inference would have
// picked int and float64 again.
var fileSize int64 = 7
var temperature float32 = 1.5

// A whole number can still start a float64 variable.
var limit float64 = 7

One var keyword, several names

The grouped form keeps a package's top-level variables in one readable block instead of a column of repeated var keywords. Note the last line: inside a group you can still declare a name with only a type, and it takes its zero value.

Example · go
// Three names, one type, no values: all three hold 0.
var x, y, z int

// Three names with values. Each type is inferred on its own.
var host, port, secure = "localhost", 8080, true

// A grouped declaration, the usual shape for package-level settings.
var (
	appName    = "soundscode"
	maxRetries = 3
	debug      bool
)

Declaration and assignment are different things

Beginners often write var twice for the same name, which fails with "attempts redeclared in this block". Declare once, then assign as often as you like. This matters as soon as a value changes over the life of a function.

Example · go
package main

import "fmt"

func main() {
	var attempts int // declaration: the variable comes into existence

	attempts = 1 // assignment: it already exists, so no var keyword
	attempts = attempts + 1

	fmt.Println(attempts)
}

// Output:
// 2

Discussion

  • Be the first to comment on this lesson.