Golang- the basis of the self-test

Balanced binary tree: the difference between the height of the left subtree and right subtree of the parent node can not be greater than 1, that is not higher than 1 layer, otherwise the tree on the imbalance,
then we must rotate node, when coding, we can recording the height of the current node, such as empty node is -1, the leaf node is 0,
height non-leaf node to the root node is incremented, such as the following figure we consider a tree of height h = 2.

 

 

 

/ * 1 to write the following logic is required to call a proc per second and ensure the program does not exit * /

import (
"runtime"
"fmt"
"time"
)


func main() {

var count int

ticket := time.NewTicker(time.Second)


for{
select {
case <-ticket.C:
ProtectRun(proc)
count++
}
}


//fmt.Println("t")
}

func ProtectRun (entry func ()) {
delay processing functions //
the defer FUNC () {
// When downtime occurs, obtain context transfer and print panic
ERR: = Recover ()
Switch ERR (type) {.
Case Runtime. error: // run-time error
fmt.Println ( "runtime error:", ERR)
default: // error Nonoperating
fmt.Println ( "error:", ERR)
}
} ()

entry()
}

func proc() {
panic("ok")
}

 

 


/ * 2. After waiting for the group to achieve timeout * /

import (
"fmt"
"sync"
"time"
)

func main() {
wg := sync.WaitGroup{}
c := make(chan struct{})
for i := 0; i < 10; i++ {
wg.Add(1)
go func(num int, close <-chan struct{}) {
defer wg.Done()
<-close
fmt.Println(num)
}(i, c)
}

if WaitTimeout (& wg, time.Second * 5) {// wg.Wait () on the outer loop, but functions as a test finish tasks; wg.Wait () placed in the cycle, is equivalent to adding a lock, a task can perform a task;
Close (C)
fmt.Println ( "timeout Exit")
}
time.sleep (time.Second 10 *)
}


WaitTimeout FUNC (WG * sync.WaitGroup, timeout time.Duration) BOOL {

// claim handwritten code
// claim sync.WaitGroup support timeout function
// If timeout returns to the timeout to true
// If WaitGroup NATURAL end returns to false


CH: = make (chan bool)

FUNC Go (CH Chan BOOL) {
wg.Wait ()
- CH <to false // returns true if the execution end
(ch)}

select {
case done := <-ch:
return done
case <-time.After(timeout):
return true
}

}

 

3. go the reasons caused the loss of resources

type query func(string) string

func exec(name string, vs ...query) string {
ch := make(chan string)
fn := func(i int) {
ch <- vs[i](name)
}
for i, _ := range vs {
go fn(i)
}
return <-ch
}

func main() {
ret := exec("111", func(n string) string {
return n + "func1"
}, func(n string) string {
return n + "func2"
}, func(n string) string {
return n + "func3"
}, func(n string) string {
return n + "func4"
})
fmt.Println(ret)
}

 

To go after use for {select {}} multiplexed

func exec(name string, vs ...query) string {
ch := make(chan string)
fn := func(i int) {
ch <- vs[i](name)
}
for i, _ := range vs {
go fn(i)
}

buffer := []string{}

OuterLoop:
for{
select {
case re := <-ch:
fmt.Println("到这了?")
fmt.Println(re)
buffer = append(buffer,re)
case <- time.After(time.Second*5):
break OuterLoop
}

}

return strings.Join(buffer,",")
}

 

 

4. enumeration class
const (
name = "menglu" 0 //
C // IOTA. 1 =
D = IOTA
)

fmt.Println(c) //1
fmt.Println(d) //2

 

5. What's wrong with the following code is written?

type Stduent struct {
Age int
}
func main() {
kv := map[string]Stduent{"menglu": {Age: 21}}
kv["menglu"].Age = 22
s := []Stduent{{Age: 21}}
s[0].Age = 22
fmt.Println(kv, s)
}


改为:
func main() {
kv := map[string]*Stduent{"menglu": &Stduent{Age: 21}}
kv["menglu"].Age = 22
s := []Stduent{{Age: 21}}
s[0].Age = 22
fmt.Println(*kv["menglu"], s)
}

 


6. Trapping
Trapping

func add(args ...int) int {}
add([]int{1, 3, 7}...)


func (s*Slice)Remove(value interface{}) error {

for i, v:= range *s {

if isEqual(value, v) {

*s =append((*s)[:i],(*s)[i + 1:]...)

return nil

}

}

returnERR_ELEM_NT_EXIST

}


A. When a goroutine after obtaining a Mutex, other goroutine can only obediently waiting, unless the goroutine release the Mutex
B. RWMutex in the case of a read lock occupied will stop writing, but do not stop reading
C. RWMutex write lock occupation case, will prevent any other goroutine (whether read and write) came exclusively by the equivalent of the entire lock goroutine

 

A. The basic idea is to package external reference source code in the vendor directory of the current project under
B. compile code that will give priority to go from vendor directory to find dependencies
after D. With the vendor directory, packaged current project code to another under machine $ GOPATH / src can be compiled by

 

91. [intermediate] on the slice or map operation, the following is correct ()
A.

92.'s were [] int

s =append(s,1)

B.

var mmap[string]int

m["one"]= 1

C.

where p [] int

s =make([]int, 0)

s =append(s,1)

D.

var mmap[string]int

m =make(map[string]int)

m["one"]= 1

Reference answer: ACD

 


D. unbuffered channel is synchronous, the channel has a non-synchronous buffer


A. select mechanism for handling asynchronous IO problems
B. select mechanisms biggest limitation is that a statement in each case must be an IO operation
C. golang support select keywords at the language level

 


33. func main() {

34. x := []string{"a", "b","c"}

35. for v := range x {

36. fmt.Print(v)

37. }

}

Answer: 012

 


panic to wait until after the end of the defer passed up.

 


2 The following code have any questions, explain why.

type student struct {
Name string
Age int
}
func pase_student() {
m := make(map[string]*student)
stus := []student{
{Name: "zhou",Age: 24},
{Name: "li",Age: 23},
{Name: "wang",Age: 22},
} for _,stu := range stus {
m[stu.Name] =&stu //问题在这里
}
}

Can not traverse the range pointer, only get a pointer to the last index of copy.

// 正确
for i:=0;i<len(stus);i++ {
m[stus[i].Name] = &stus[i]
}
for k,v:=range m{
println(k,"=>",v.Name)
}

 


select as long as there is a case could return, then immediately executed.
If at the same time when the case could have a plurality of return is a pseudo-random manner any extraction performed.
If a case is not able to return may be performed "default" block.


func calc(indexstring, a, bint) int {
ret := a+ b
fmt.Println(index,a, b, ret)
return ret
}
func main() {
a := 1
b := 2
defer calc("1", a,calc("10", a, b)) a = 0
defer calc("2", a,calc("20", a, b)) b = 1
}


index: 1 is definitely the last to perform, but the index: 1. The third parameter is a function, it is the first to be called

 

func main() {

23. strs := []string{"one","two", "three"}

24.

25. for _, s := range strs {

26. go func() {

27. time.Sleep(1 * time.Second)

28. fmt.Printf("%s ", s)

29. }()

30. }

31. time.Sleep(3 * time.Second)

}

Reference answer: three threethree


Through the array is normal, the problem is go func (s2 string) anonymous function requires mass participation.

 

type Slice []int

62. func NewSlice() Slice {

63. return make(Slice, 0)

64. }

65. func (s* Slice) Add(elem int) *Slice {

66. *s = append(*s, elem)

67 fmt.Print (battery)

68. return s

69. }

70. func main() {

71. s := NewSlice()

72. defer s.Add(1).Add(2)

73. s.Add(3)

}

Answer: 132

2 as a function of a first read defer, pushed to the bottom of the stack, and then perform normal 13

 

 

The following code 8 What is the problem?

type UserAges struct {
ages map[string]int
sync.Mutex
}
func(ua*UserAges)Add(name string, age int) {
ua.Lock()
deferua.Unlock()
ua.ages[name] = age
}
func(ua*UserAges)Get(name string)int {
ifage, ok := ua.ages[name]; ok {
return age
}
return-1
}


To read and write the same time lock

func (ua *UserAges)Get(namestring)int {
ua.Lock()
deferua.Unlock()
ifage, ok := ua.ages[name]; ok {
return age
}
return-1
}


10 The following code can be compiled in the past it? why?

package main
import ( "fmt")
type People interface {
Speak(string) string
}
type Stduent struct{}
func (stu*Stduent) Speak(think string)(talk string) {
if think == "bitch" {
talk = "Youare a good boy"
} else {
talk = "hi"
}
return
}
func main() {
var peo People = Stduent{}
think := "bitch"
fmt.Println(peo.Speak(think))
}

The answer is yes, this is achieved with the use of the interface.

 

switch. (type) {} can only be used type interface {}


var i interface{}
i = 1
switch i.(type){
case int:
fmt.Println("int")
}

This not compile
I: =. 1
Switch I (type). {
Case int:
fmt.Println ( "int")
}


out of the new pointer, make out value


list := new([]int)
*list = append(*list,1)

list2 := make([]int,0)
list2 = append(list2,1)


Structure for comparing the time, only the structure of the same type of comparison can, not only the structure is the same as the number of attributes related to the type attribute is also associated with the order.


Pointer is null var a * int = nil and x == nil null value is different things


Unlike variables constant allocate memory at runtime, compiler constants would normally be deployed directly preprocessing stage, as instruction data,


const cl = 100

fmt.Println (Cl)
fmt.Println (& Cl) constant does not allocate memory


type M1 int // M1 for the new type, we need strong turn assignment
type M2 = int // M2 aliases

were int = 9

was i1 M1 = M1 (i)
was i2 M2 = i

fmt.Println(i1,i2)

 


FUNC Test () [] FUNC () {
var funs [] FUNC ()
for I: = 0; I <2; I ++ {
funs = the append (funs, FUNC () {// anonymous function is the closure, with a delay execution characteristics of static and stored, either directly to the anonymous transfer function parameters, or values stored in the outer layer defined variables;
the println (& I, I)
})
}
return funs
}


funs := test()
for _, f :=range funs{
f()
}


func main() {

funs := test()
for _, f :=range funs{
f()
}
}

 

x := i

funs = append(funs, func() {
println(&x, x)
})

 

###################################################################
grpc:

// grpc service sends a signal to detect whether the connection;
signal.Notify (C, syscall.SIGHUP, syscall.SIGQUIT, syscall.SIGTERM, syscall.SIGINT)
for {
S: = <-C
log.info ( "GET A Signal S% ", s.String ())
Switch S {
Case syscall.SIGQUIT, syscall.SIGTERM, syscall.SIGINT:
svc.Close ()
log.info (" Zeus-Service-Exit ")
time.sleep (time.Second)
return
Case syscall.SIGHUP:
default:
return
}
}

Passed through between the http service header form, are passed through between rpc service rpc metadata form.

1. serve to initialize a database connection pool, etc.
... created inside rpc service,
NET / rpc / Warden
FUNC New (conf.Config C *, S * v1srv.ZeusService) * {warden.Server
WS: = warden.NewServer (nil )
v1pb.RegisterZeusServer (ws.Server (), S)
WS, ERR: = ws.Start ()
! = nil {IF ERR
panic (ERR)
}
return WS
}

If we achieve with RPC socket, so you can get a performance advantage. In the case of large concurrent, RPC's performance is better than RESTful
so under normal circumstances, we are providing services internally with rpc, outside with RESTful service

golang official provided us with a net / rpc library, which supports tpc, http, JSONRPC data transmission. But it can only go for internal use, and why?
Go because it uses a built-in library (encoding / gob) to encode and decode. If you need cross-platform we need other rpc a framework, such as thrift, gRPC etc.


Remote call net / rpc there are a number of additional conditions:

1. The function must be derived (initials)
2 must have two types of parameters derived
3. The first parameter is the received parameter, the second parameter is returned to the customer - client parameter, the second parameter must be a pointer type
4 also has a function return value error


type Arith int

func (t *Arith) Multiply(args *string, reply *int) error {
return nil
}

arith := new(Arith)
rpc.Register(arith)
rpc.HandleHTTP()
l, e := net.Listen("tcp", ":1212")
if e != nil {
log.Fatal("listen error: ", e)
}
http.Serve(l, nil)

A simple analysis above example, the first instance of an object is Arith arith, then to arith registered rpc service, and then mount the http service rpc above,
when the http service opens when we will be able to call arith by rpc client rpc methods in line with the standards of

// use three methods, rpc, net, http


//客户端
client, err := rpc.DialHTTP("tcp", "127.0.0.1:1212")
client.Call("Arith.Multiply", "call", &reply)

 

How to capture the exception go routing, and Recovery:
One method is an abstract method,
ProtectedRun (F FUNC ()) {
the defer FUNC () {
ERR: = Recover ()
}
F ()
}

go ProtectRun()


Another method is to use a reflective cut

func newF(){

go func(){
defer func(){
err := recover()

ff := reflect.ValueOf(f)
ff.Call()
}
}

}

 


################################################## ###########################################
nested service goroutine

When a service contains multiple sub-services, each sub service and have goroutine, how close this was only goroutine child services?

func main(){

CTX, Cancel: = context.WithCancel (context.Backgroud ())
Go doStuff (CTX)

time.sleep (10 * time.Seconds)
Cancel () // turn off the sub-services, to close the channel to pass information to context;

}

 

func doStuff(ctx context.Backgroud){
for{
select{
case <-ctx.Done():
return
default:
fmt.Print("working")
}
}
}

 

// two single embodiment modes


import "sync"
import "sync/atomic"

var initialized uint32
...

func GetInstance() *singleton {

if atomic.LoadUInt32(&initialized) == 1 {
return instance
}

mu.Lock()
defer mu.Unlock()

if initialized == 0 {
instance = &singleton{}
atomic.StoreUint32(&initialized, 1)
}

return instance
}

 

import (
"sync"
)

type singleton struct {
}

var instance *singleton
var once sync.Once

func GetInstance() *singleton {
once.Do(func() {
instance = &singleton{}
})
return instance
}

 

Guess you like

Origin www.cnblogs.com/ruili07/p/11458851.html