Variables & :=
In PHP, a variable springs into existence the first time you assign to it. $platform = 3; and there it is. Assign a string to it later and PHP shrugs: it's a string now.
Go wants a little more ceremony up front, and in return it never lets a variable quietly change what it is.
Three ways to say the same thing
var station string = "Bank" // the full form var platform = 3 // inferred: int open := true // the short form
All three declare a variable. The type always goes after the name, like the function parameters in 0.2.
var name type = valueis the full version. You'll rarely write all three parts, because Go can see that"Bank"is a string.var name = valuedrops the type and lets Go infer it.name := valueis the short form, and it's what you'll write most of the time. Read:=as "declare and assign". It only works inside a function.
There's a fourth shape you'll also see a lot: var name type with no value at all. That gives you the type's zero value, 0, "" or false, exactly as lesson 1.4 describes. No null, no "undefined variable" warning.
Whichever form you use, the type is fixed for good. platform above is an int forever, so platform = "three" is a compile error, not a type juggle. (Lesson 1.3 covers types and converting between them.)
Tip
The convention most Go code follows: use := when you have a value to start with, and var x T when you want the zero value and will fill it in later. At package level, outside any function, var is your only option.
= vs :=
This is the distinction that matters. := declares a new variable. = assigns to one that already exists.
count := 0 // declares count count = 5 // assigns to it count := 10 // error: no new variables on left side of :=
There's one wrinkle: := with several names on the left only needs one of them to be new. The others are just assigned. That's handy later, when functions return a value and an error, and you'll meet it constantly in Unit 4.
Swapping without a temp
Several variables can be assigned at once, and Go works out the whole right-hand side before assigning anything. So swapping is one line, no $tmp:
from, to = to, from
That's PHP's [$from, $to] = [$to, $from], minus the throwaway arrays. Check the Interchange tab for both.
Unused is an error
You met this in 0.2: a local variable you declare and never use stops the build with declared and not used: x. If you genuinely need to throw a value away, assign it to the blank identifier, _, which accepts anything and keeps nothing.
| 14:02 | debug := true, "just for a second" |
|---|---|
| 14:02 | declared and not used: debug |
| 14:03 | _ = debug |
| 14:03 | (it is now 2031 and that line is still there) |
Block scope (and the shadow it casts)
A PHP variable belongs to the whole function. Set $status inside an if, and it's still there after the closing brace.
A Go variable belongs to the nearest pair of braces. Declare it inside an if, a loop or a bare { } block, and it's gone at the closing brace. Try to use it afterwards and the compiler says undefined.
That combines with := to produce Go's best-known beginner bug:
origin := "Ealing Broadway" if reversed { origin := "Epping" // a new, inner origin } // origin is still "Ealing Broadway" here
Two variables, one name, two scopes:
flowchart TB
accTitle: Shadowing with := inside an if block
accDescr: Before the if block, origin is Ealing Broadway. Inside the block, origin := "Epping" declares a second, separate variable that happens to share the name. At the closing brace the inner origin disappears, and the outer one was never touched, so it is still Ealing Broadway.
o1["origin = Ealing Broadway"] --> blk
subgraph blk ["Inside if reversed"]
o2["origin := Epping<br/>a second, new variable"]
end
blk -->|"closing brace"| o3["origin is still<br/>Ealing Broadway"]
Mind the gap
:= inside a block shadows the outer variable. In PHP, $origin = 'Epping'; inside the if would update the one you already have. In Go, := inside a new block always declares a fresh variable, even if one with the same name exists outside. The outer one is untouched, and the inner one disappears at the brace. When you mean "update", use =. Here the compiler happens to catch it, because the inner origin is never used. When the inner one is used, it compiles, and the bug ships.
The exercise is exactly this bug, caught by the compiler. Read the error message carefully: it's more helpful than it first looks.
Recap
var x T = v,var x = vandx := vall declare a variable.:=is the everyday form, but works only inside functions.var x Tgives the zero value.- A variable's type is fixed when it's declared, whether you write it or Go infers it.
:=declares,=assigns.a, b = b, aswaps.- Unused locals don't compile.
_discards a value. - Variables live in their
{ }block.:=in an inner block makes a new variable that shadows the outer one.