Hello,GO!
package main // Define package name func main() { print("Hello,Go") }
main function points
- ++No parameter, no return value++
- The main method must be in the main package
- go run main.go can be executed
- If the file is not called main Go, you need to go build and then go run
Package declaration - package declaration
- Syntax form: package xxx
- Combination of letters and underscores
- ++Can have a different name from the folder++
- The statements under the same folder are consistent
- Syntax form of import package: import [alias] xxx
- If the package is imported but not used, an error will be reported
- Anonymous introduction: one more underline in front
Basic type
String
- String enclosed in double quotation marks, "escape"
- Use back quotation marks to enclose a large paragraph of text (which needs to be wrapped), and there is no need to escape the double quotation marks inside
goland will help escape, okay - len() calculates the byte length
len("hello") / / = 6
Calculation length: utf8 Runecountinstring ("hello") / / 2 - Main methods of strings: find and replace; Case conversion; Substring correlation; equal
rune type
The intuitive understanding of rune type is: character
Run is not byte
The essence of rune is int32. A rune has four bytes
There is no char in go, only rune
Run is not a number, nor a char, nor a byte!
(but not commonly used in practice)
bool,int,unit.float
- bool: true,false
- int8,int16,int32,int54,++int++
- Unit8, Unit16, unit32, unit64, + unit + + (unsigned number)
- float32,float64
byte type
++byte is essentially unit8++
The corresponding operation package is on bytes
Type summary
- The number type of golang clearly indicates the length and signed number
- golang won't do type conversion for you. Different types cannot be compiled. Therefore, + + string can only be spliced with string++
- golang has a very special rune type, which is close to the concept of character or character in general language. In the case of + + non interview, it can be understood as "rune = character"++
- string never find the strings package
Variable declaration
Variable declaration var
- var, syntax: var name type=value
- Whether a global variable or a package variable is determined by the case of the initial letter
For example:
var Global = "global variable" / / Global is capitalized and can be accessed globally
var local = "package variable" / / the initial letter is lowercase. It can only be used in this package, and sub packages cannot be used
var ( //Block declaration First string ="abc" second int32 = 16 )
golang is a strongly typed language with inconsistent types = = unequal judgment
Variable declaration:=
- It can only be used for local variables, that is, inside methods
- golang uses type inference to infer types. Numbers will be interpreted as int or float64. (therefore, other types of numbers have to be declared with var
func main(){ a:=13 println(a) b:="Hello" println(b) }
Variable declaration fallibility
- The variable is declared unused: like import, if it is not used, the compilation will not pass
- type mismatch
- Variables can only be declared once under the same scope
Constant declaration const
- Whether the initial capital controls accessibility: capital package
- Hump naming
- Support type inference
- The value cannot be modified
const internal = "Accessible in package" const External = "Accessible outside the package"
Method declaration
Four parts:
- Keyword func
- Method name: whether the initial letter is capitalized determines the scope
- Parameter list []
- Return to list []
Go supports multiple return values
Multiple return values. The parameter has a name, but the return value does not:
func Fun1(a string, b int) (int, string){ return 0,"Hello" }
The returned value has a name, which can be copied internally and then returned. You can also ignore age and name and directly return others:
func Fun2(a string, b int) (age int, name string){ age=19 name="Tom" < return }
Single return value
func Fun0(a string) string{ return "Hello, "+name }
Indefinite parameter - slice (later)
_,d :=Fun2(a:"a",b:"b")
Underline_ Anonymous
- golang supports multiple return values, which is a big difference
- The scope of golang method is the same as that of variable, which is controlled by case
- The return value of golang can have a name. By giving a name, the caller can clearly know what you are returning
The simplest web server
package main // Define package name import ( "fmt" "log" "net/http" ) func handler(w http.ResponseWriter, r *http.Request) { fmt.Fprintf(w, "Hi there, Ilove %s!", r.URL.Path[1:]) } func main() { http.HandleFunc("/", handler) log.Fatal(http.ListenAndServe(":8088", nil)) }
Add several routes
func home(w http.ResponseWriter, r *http.Request){ fmt.Fprintf(w,"This is the home page") } func user(w http.ResponseWriter, r *http.Request){ fmt.Fprintf(w,"This is the user") } func main(){ http.HandleFunc("/",home) http.HandleFunc("/user",user) log.Fatal(http.ListenAndServe(":8088", nil)) }
fmt formatted output
API to return string
str:=fmt.Sprintf("hello,I am %s",name)
Direct output
fmt.Printf("hello,i am %s",name)
Placeholder:
- %s string% d integer
- %The default format for the v value. When printing a structure, the plus sign mark (% + v) adds a field name
- %#Go syntax representation of v corresponding value
- %The syntax value of Go T represents the corresponding type
- %%A percent sign on a letter is not a placeholder for a value
package main import ( "fmt" ) type Sample struct { a int str string } func main() { s := Sample{a: 1, str: "hello"} fmt.Printf("%v\n", s) //{1, hello} fmt.Printf("%+v\n", s) //{a:1, str:hello} fmt.Printf("%#v\n", s) //main.Sample{a:1, str:"hello"} fmt.Printf("%T\n", s) // main.Sample fmt.Printf("%%\n", s.a) // % %!(EXTRA int=1) }
Arrays and slices
Arrays are similar to arrays in other languages. The syntax is: [cap]type
- Initialize the length (capacity) to be specified
- Direct initialization
- Accessing elements in the form of arr[i]
- len and cap operations are used to get the length of the array
package main // Define package name import "fmt" func main() { //Directly initialize an array of three elements. One more or one less in braces will not pass the compilation a1 := [3]int{9, 8, 7} fmt.Printf("a1: %v, len: %d, cap: %d\n", a1, len(a1), cap(a1)) //Initializes an array of three elements, all of which are 0 var a2 [3]int fmt.Printf("a2: %v, len: %d,cap: %d\n", a2, len(a2), cap(a2)) //a1=append(a1,a2) array does not support append operation //Index by subscript fmt.Printf("a1[1]:%d", a1[1]) //Beyond the subscript range, crash directly and fail to compile //fmt.Printf("a1[99]: %d",a1[99]) }
The results are as follows:
a1: [9 8 7], len: 3, cap: 3 a2: [0 0 0], len: 3,cap: 3 a1[1]:8
Slice, syntax: [] type
- Direct initialization
- Make initialization: make([]type, length, capacity)
- Accessing elements in the form of arr[i]
- Append append element
- len get the number of elements
- Get slice capacity from cap
- Recommended writing method: S1: = make ([] type, 0, capacity)
package main import "fmt" func main() { s1 := []int{1, 2, 3, 4} //Directly initializes the slice of 4 elements fmt.Printf("s1: %v, len: %d, cap: %d\n", s1, len(s1), cap(s1)) s2 := make([]int, 3, 4) //A slice with three elements and a capacity of 4 is created fmt.Printf("s2: %v, len: %d, cap: %d\n", s2, len(s2), cap(s2)) s2 = append(s2, 7) //An element is added in the back, which does not exceed the capacity limit and will not be expanded fmt.Printf("s2: %v, len: %d, cap: %d\n", s2, len(s2), cap(s2)) s2 = append(s2, 8) //Add an element to trigger capacity expansion fmt.Printf("s2: %v, len: %d, cap: %d\n", s2, len(s2), cap(s2)) s3 := make([]int, 4) //Only one parameter is passed in, which means to create a with four elements and a capacity of four elements fmt.Printf("s3: %v, len: %d, cap: %d\n", s3, len(s3), cap(s3)) //Index by subscript fmt.Printf("s3[2]: %d", s3[2]) //Out of subscript range, crash directly //runtime error: index out of range[99] with length 4 //fmt.Printf("s2[99]:%d",s3[99]) }
The results are as follows:
s1: [1 2 3 4], len: 4, cap: 4 s2: [0 0 0], len: 3, cap: 4 s2: [0 0 0 7], len: 4, cap: 4 s2: [0 0 0 7 8], len: 5, cap: 8 s3: [0 0 0 0], len: 4, cap: 4 s3[2]: 0
array | section | |
---|---|---|
Direct initialization | support | support |
make | I won't support it | support |
Access element | arr[i] | arr[i] |
len | length | Number of existing elements |
cap | length | capacity |
append | I won't support it | support |
Can I expand the capacity | may not | sure |
There is almost no error with slicing
Sub slice
Both arrays and slices can obtain sub slices in the form of [start:end]:
- arr[start:end], get the elements between [start, end]
- arr[:end], get the elements between [0, end]
- arr[start:], get the elements between [start,len(arr)]
Left close right open principle
How to understand slicing
The most intuitive comparison: ArrayList, that is, the implementation of List based on array, and the bottom layer of slice is also array
Difference from ArrayList:
- Slicing operations are limited, and random addition and deletion are not supported (i.e. there are no add and delete methods, so you need to write your own code)
- Only append operation
- Slicing supports sub slicing and shares the underlying array with the original slicing
Shared bottom layer (optional)
Core: shared array
Whether sub slices and slices will affect each other or not, we can grasp one point: do they still share arrays?
If there is no change in their structure, they must be shared; But when the structure changes, it may not be shared
package main import "fmt" func ShareSlice() { s1 := []int{1, 2, 3, 4} s2 := s1[2:] fmt.Printf("s1: %v,len: %d,cap: %d\n", s1, len(s1), cap(s1)) fmt.Printf("s2: %v,len: %d,cap: %d\n", s2, len(s2), cap(s2)) s2[0] = 99 fmt.Printf("s1: %v,len: %d,cap: %d\n", s1, len(s1), cap(s1)) fmt.Printf("s2: %v,len: %d,cap: %d\n", s2, len(s2), cap(s2)) s2 = append(s2, 199) fmt.Printf("s1: %v,len: %d,cap: %d\n", s1, len(s1), cap(s1)) fmt.Printf("s2: %v,len: %d,cap: %d\n", s2, len(s2), cap(s2)) s2[1] = 1999 fmt.Printf("s1: %v,len: %d,cap: %d\n", s1, len(s1), cap(s1)) fmt.Printf("s2: %v,len: %d,cap: %d\n", s2, len(s2), cap(s2)) } func main() { ShareSlice() }
The results are as follows:
s1: [1 2 3 4],len: 4,cap: 4 s2: [3 4],len: 2,cap: 2 s1: [1 2 99 4],len: 4,cap: 4 s2: [99 4],len: 2,cap: 2 s1: [1 2 99 4],len: 4,cap: 4 s2: [99 4 199],len: 3,cap: 4 s1: [1 2 99 4],len: 4,cap: 4 s2: [99 1999 199],len: 3,cap: 4
for
for is similar to other grammars in three forms:
- for {}, an infinite loop similar to while
func ForLoop() { arr := []int{9, 8, 7, 6} index := 0 for { if index == 3 { break } fmt.Printf("%d=>%d,", index, arr[index]) index++ } fmt.Printf("for loop end\n") }
- fori, which generally circulates according to the subscript
func ForI() { arr := []int{9, 8, 7, 6} for i := 0; i < len(arr); i++ { fmt.Printf("%d=>%d,", i, arr[i]) } fmt.Printf("for i loop end\n") }
- for range is the most special range traversal
func ForR() { arr := []int{9, 8, 7, 6} //If you only need value, you can use_ Replace index //If you only need index, you can also remove it and write it as for index:=range arr for index, value := range arr { fmt.Printf("%d=>%d,", index, value) } fmt.Printf("for r loop end") }
- break and continue are the same as other languages
if-else
If else is similar to other languages
if condition{...}
else if condition{...}
else{...}
If else with local variable declaration:
func IfUsingNewVariable(start int, end int) { if distance := end - start; distance > 100 { fmt.Printf("Too far away:%d\n", distance) } else { // else branches can also be absent fmt.Printf("Not far away:%d\n",distance) } //distance cannot be accessed here }
- distance can only be used in if blocks or all subsequent else blocks
- Without the if else block, it can no longer be used
switch
switch is similar to other languages
switch can be followed by a string of basic type or a structure that meets specific conditions
The biggest difference: don't add break!
func ChooseFruit(fruit string) { switch fruit { case "Apple": fmt.Println("This is an apple") case "strawberry", "Blueberry": fmt.Println("This is a berry") default: fmt.Printf("New fruit:%s\n", fruit) } }