mirror of
https://github.com/golang/go
synced 2024-11-22 01:34:41 -07:00
add sections about types and constants
R=gri DELTA=133 (124 added, 0 deleted, 9 changed) OCL=15122 CL=15143
This commit is contained in:
parent
0a7e4a7415
commit
c7ebfed655
@ -45,7 +45,7 @@ to store Unicode strings represented in UTF-8.
|
|||||||
|
|
||||||
The built-in function "print()" has been used during the early stages of
|
The built-in function "print()" has been used during the early stages of
|
||||||
development of the language but is not guaranteed to last. Here's a better version of the
|
development of the language but is not guaranteed to last. Here's a better version of the
|
||||||
program that doesn't depend on this "print()":
|
program that doesn't depend on "print()":
|
||||||
|
|
||||||
--PROG progs/helloworld2.go
|
--PROG progs/helloworld2.go
|
||||||
|
|
||||||
@ -103,20 +103,20 @@ or we could go even shorter and write the idiom
|
|||||||
s := "";
|
s := "";
|
||||||
|
|
||||||
The := operator is used a lot in Go to represent an initializing declaration.
|
The := operator is used a lot in Go to represent an initializing declaration.
|
||||||
(For those who know Limbo, it's the same, except notice that there is no
|
(For those who know Limbo, its := construct is the same, but notice
|
||||||
colon after the name in a full "var" declaration.)
|
that Go has no colon after the name in a full "var" declaration.)
|
||||||
And here's one in the "for" clause on the next line:
|
And there's one in the "for" clause on the next line:
|
||||||
|
|
||||||
--PROG progs/echo.go /for/
|
--PROG progs/echo.go /for/
|
||||||
|
|
||||||
The "Flag" package has parsed the arguments and left the non-flags in
|
The "Flag" package has parsed the arguments and left the non-flag arguments
|
||||||
a list that can be iterated over in the obvious way.
|
in a list that can be iterated over in the obvious way.
|
||||||
|
|
||||||
The Go "for" statement differs from that of C in a number of ways. First,
|
The Go "for" statement differs from that of C in a number of ways. First,
|
||||||
it's the only looping construct; there is no "while" or "do". Second,
|
it's the only looping construct; there is no "while" or "do". Second,
|
||||||
there are no parentheses on the clause, but the braces on the body
|
there are no parentheses on the clause, but the braces on the body
|
||||||
are mandatory. Later examples will show some other ways "for"
|
are mandatory. (The same applies to the "if" statement.) Later examples
|
||||||
can be written.
|
will show some other ways "for" can be written.
|
||||||
|
|
||||||
The body of the loop builds up the string "s" by appending (using +=)
|
The body of the loop builds up the string "s" by appending (using +=)
|
||||||
the flags and separating spaces. After the loop, if the "-n" flag is not
|
the flags and separating spaces. After the loop, if the "-n" flag is not
|
||||||
@ -132,4 +132,104 @@ The "sys" package is built in and contains some essentials for getting
|
|||||||
started; for instance, "sys.argc()" and "sys.argv(int)" are used by the
|
started; for instance, "sys.argc()" and "sys.argv(int)" are used by the
|
||||||
"Flag" package to access the arguments.
|
"Flag" package to access the arguments.
|
||||||
|
|
||||||
More to come.
|
An Interlude about Types
|
||||||
|
----
|
||||||
|
|
||||||
|
Go has some familiar types such as "int" and "float", which represent
|
||||||
|
values of the ''appropriate'' size for the machine. It also defines
|
||||||
|
specifically-sized types such as "int8", "float64", and so on, plus
|
||||||
|
unsigned integer types such as "uint", "uint32", etc. And then there
|
||||||
|
is a "byte" synonym for "uint8", which is the element type for
|
||||||
|
strings.
|
||||||
|
|
||||||
|
Speaking of "string", that's a built-in type as well. Strings are
|
||||||
|
<i>immutable values</i> -- they are not just arrays of "byte" values.
|
||||||
|
Once you've built a string <i>value</i>, you can't change it, although
|
||||||
|
of course you can change a string <i>variable</i> simply by
|
||||||
|
reassigning it. This snippet from "strings.go" is legal code:
|
||||||
|
|
||||||
|
--PROG progs/strings.go /hello/ /ciao/
|
||||||
|
|
||||||
|
However the following statements are illegal because they would modify
|
||||||
|
a "string" value:
|
||||||
|
|
||||||
|
s[0] = 'x';
|
||||||
|
(*p)[1] = 'y';
|
||||||
|
|
||||||
|
In C++ terms, Go strings are a bit like "const strings", while pointers
|
||||||
|
to strings are analogous to "const string" references.
|
||||||
|
|
||||||
|
Yes, there are pointers. However, Go simplifies their use a little;
|
||||||
|
read on.
|
||||||
|
|
||||||
|
Arrays are declared like this:
|
||||||
|
|
||||||
|
var array_of_int [10]int;
|
||||||
|
|
||||||
|
Arrays, like strings, are values, but they are mutable. This differs
|
||||||
|
from C, in which "array_of_int" would be usable as a pointer to "int".
|
||||||
|
In Go, since arrays are values, it's meaningful (and useful) to talk
|
||||||
|
about pointers to arrays.
|
||||||
|
|
||||||
|
The size of the array is part of its type; however, one can declare
|
||||||
|
an <i>open array</i> variable, to which one can assign any array value
|
||||||
|
with the same element type.
|
||||||
|
(At the moment, only <i>pointers</i> to open arrays are implemented.)
|
||||||
|
Thus one can write this function (from "sum.go"):
|
||||||
|
|
||||||
|
--PROG progs/sum.go /sum/ /^}/
|
||||||
|
|
||||||
|
and invoke it like this:
|
||||||
|
|
||||||
|
--PROG progs/sum.go /1,2,3/
|
||||||
|
|
||||||
|
Note how the return type ("int") is defined for "sum()" by stating it
|
||||||
|
after the parameter list. Also observe that although the argument
|
||||||
|
is a pointer to an array, we can index it directly ("a[i]" not "(*a)[i]").
|
||||||
|
The expression "[]int{1,2,3}" -- a type followed by a brace-bounded expression
|
||||||
|
-- is a constructor for a value, in this case an array of "int". We pass it
|
||||||
|
to "sum()" by taking its address.
|
||||||
|
|
||||||
|
The built-in function "len()" appeared there too - it works on strings,
|
||||||
|
arrays, and maps, which can be built like this:
|
||||||
|
|
||||||
|
m := map[string] int {"one":1 , "two":2}
|
||||||
|
|
||||||
|
At least for now, maps are <i>always</i> pointers, so in this example
|
||||||
|
"m" has type "*map[string]int". This may change.
|
||||||
|
|
||||||
|
You can also create a map (or anything else) with the built-in "new()"
|
||||||
|
function:
|
||||||
|
|
||||||
|
m := new(map[string] int)
|
||||||
|
|
||||||
|
The "new()" function always returns a pointer, an address for the object
|
||||||
|
it creates.
|
||||||
|
|
||||||
|
An Interlude about Constants
|
||||||
|
----
|
||||||
|
|
||||||
|
Although integers come in lots of sizes in Go, integer constants do not.
|
||||||
|
There are no constants like "0ll" or "0x0UL". Instead, integer
|
||||||
|
constants are evaluated as ideal, arbitrary precision values that
|
||||||
|
can overflow only when they are assigned to an integer variable of
|
||||||
|
some specific size.
|
||||||
|
|
||||||
|
const hard_eight = (1 << 100) >> 97 // legal
|
||||||
|
|
||||||
|
There are nuances that deserve redirection to the legalese of the
|
||||||
|
language specification but here are some illustrative examples:
|
||||||
|
|
||||||
|
var a uint64 = 0 // a has type uint64, value 0
|
||||||
|
a := uint64(0) // equivalent; uses a "conversion"
|
||||||
|
i := 0x1234 // i gets default type: int
|
||||||
|
var j int = 1e6 // legal - 1000000 is representable in an int
|
||||||
|
x := 1.5 // a float
|
||||||
|
i3div2 = 3/2 // integer division - result is 1
|
||||||
|
f3div2 = 3./2. // floating point division - result is 1.5
|
||||||
|
|
||||||
|
Conversions only work for simple cases such as converting ints of one
|
||||||
|
sign or size to another, and between ints and floats, plus a few other
|
||||||
|
simple cases. There are no automatic conversions of any kind in Go,
|
||||||
|
other than that of making constants have concrete size and type when
|
||||||
|
assigned to a variable.
|
||||||
|
13
doc/progs/strings.go
Normal file
13
doc/progs/strings.go
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
// Copyright 2009 The Go Authors. All rights reserved.
|
||||||
|
// Use of this source code is governed by a BSD-style
|
||||||
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
|
package main
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
s := "hello";
|
||||||
|
if s[1] == 'e' { print("success") }
|
||||||
|
s = "good bye";
|
||||||
|
var p *string = &s;
|
||||||
|
*p = "ciao";
|
||||||
|
}
|
19
doc/progs/sum.go
Normal file
19
doc/progs/sum.go
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
// Copyright 2009 The Go Authors. All rights reserved.
|
||||||
|
// Use of this source code is governed by a BSD-style
|
||||||
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
|
package main
|
||||||
|
|
||||||
|
func sum(a *[]int) int { // returns an int
|
||||||
|
s := 0;
|
||||||
|
for i := 0; i < len(a); i++ {
|
||||||
|
s += a[i]
|
||||||
|
}
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
s := sum(&[]int{1,2,3}); // pass address of int array
|
||||||
|
print(s, "\n");
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user