Upgrade to Pro — share decks privately, control downloads, hide ads and more …

The Go programming language

yageek
April 24, 2015

The Go programming language

A fast smooth introduction to the language

yageek

April 24, 2015
Tweet

More Decks by yageek

Other Decks in Programming

Transcript

  1. The Go programming language A fast smooth introduction to the

    language 24 April 2015 Yannick Heinrich Software Developer, OpenWeb Technology
  2. Go history Project started as internal project at Google in

    2007 Open-sourced in 2009 with a BSD-style license Last stable release 1.4.2 (2014/12/10) Gopher by Renée French (http://www.reneefrench.com)
  3. Go is blessed by the Gods Rob Pike (Golang Project

    Leader, Unix, UTF-8, Plan 9, Inferno) Kenneth Thomson (Unix, C, UTF-8, Plan 9, Turing Award 1983) Robert Griesemer (Java HotSpot, Google v8)
  4. Who uses Go? Internet: - Youtube (http://code.google.com/p/vitess/) , Disqus (http://blog.disqus.com/post/51155103801/trying-out-this-go-thing)

    , Tumblr (https://github.com/tumblr/gocircuit) , Twitch (http://blog.twitch.tv/2014/04/technically-speaking-group-chat-and-general-chat-engineering/) , Heroku, Cloudfare, SoundCloud, Scalingo Nerds: - Github (http://techno-weenie.net/2013/11/2/key-value-logs-in-go/) , Sourcegraph (https://sourcegraph.com/) Lightweight virtualization: - Docker (https://www.docker.com/) UFOS: - BBC (http://www.quora.com/Go-programming-language/Is-Google-Go-ready-for-production-use/answer/Kunal-Anand) , Novartis (https://plus.google.com/114945221884326152379/posts/d1SVaqkRyTL) , Thomson Reuters (https://groups.google.com/forum/?fromgroups#!topic/golang-nuts/ikt3hcIqicA) Farmers: - Zynga (http://code.zynga.com/2013/08/zbase-a-high-performance-elastic-distributed-key-value-store/) More Golang Users (https://code.google.com/p/go-wiki/wiki/GoUsers)
  5. Gopher is the new hipster Interest is growing good The

    growth of Google searches for the term "golang" over the years Dozen of Go User Groups Big meetings: dotGo, GopherIndia, GothamGo, GopherCon, GoCon
  6. Adopt Go ! Iron.io rewrites their execution job system in

    go: Dropped from 30 to 2 servers and the second server was used only for redundancy. CPU utilization dropped to less than 5%. Memory usage dropped. Only a "few hundred KB's of memory (on startup) vs our Rails apps which were ~50MB (on startup)". Iron.IO - How We Went from 30 Servers to 2: Go (http://blog.iron.io/2013/03/how-we-went-from-30-servers-to-2-go.html) GopherCon 2014 From Node.js to Go by Kelsey Falter (https://www.youtube.com/watch?t=21&v=mBy20FgB68Q)
  7. Go is your best friend Native and static compiled Polyglot

    Garbage Collected Tolerant Strongly typed
  8. Native and static compiled No f*** JVM Fast compilation, as

    fast as scripting No shared libraries All stu packaged in one binary, runtime included
  9. Polyglot Linux, Mac Os X, FreeBSD, NetBSD, OpenBSD, MS-Windows and

    Plan 9 (just in case) O cial supported architectures : x86, amd64, arm32, arm64 - Cross compilation for free $ GOOS=windows GOARCH=386 go build main.go $ GOOS=darwin GOARCH=amd64 go build main.go $ GOOS=freebds GOARCH=arm GOARM=5 go build main.go Smart build constraints // +build linux,386 darwin,!cgo // File name constraints: // *_GOOS // *_GOARCH // *_GOOS_GOARCH
  10. Garbage Collected Feels good like C, C++ without malloc and

    free No pointer arithmetics Mark and Sweep GC
  11. Tolerant For lazy person: easy to work with C code

    with cgo package main import "fmt" // #include <stdio.h> import "C" func main() { n, err := C.getchar() fmt.Print(n, err) }
  12. Tolerant For smart people: easy to ne tune with assembly

    // Snippet extracted from: arith_386.s // This file provides fast assembly versions for the elementary // arithmetic operations on vectors implemented in arith.go. // func mulWW(x, y Word) (z1, z0 Word) TEXT ·mulWW(SB),NOSPLIT,$0 MOVL x+0(FP), AX MULL y+4(FP) MOVL DX, z1+8(FP) MOVL AX, z0+12(FP) RET
  13. Strongly typed If it compiles, it (should) works (usage of

    re ection excepted) All cast are explicit
  14. One syntax to rule them all Syntax is not important...

    - unless you are a programmer, Rob Pike package main ; import "fmt" ; func main() { fmt.Println("Hello, "); } $ go fmtmain.go Annoying at start Fucking good at the end go fmt could be easily integrated with Vim, Sublime Text or Atom package main import "fmt" func main() { fmt.Println("Hello, ") } Run
  15. Variables package main import "fmt" func main() { a :=

    3.14 b := "some string" var c float32 = 3.14 var d string = "some string" fmt.Println("a:", a) fmt.Println("b:", b) fmt.Println("c:", c) fmt.Println("d:", d) } Run
  16. Functions package main import "fmt" func square(n int) int {

    return n * n } func rectanglePerimeter(l, L int) int { return (l + L) * 2 } func main() { fmt.Println("Square 6:", square(6)) fmt.Println("Rectangle Perimeter (3,6):", rectanglePerimeter(3, 6)) someFunction := func(n int) int { return n + 4 } fmt.Println("someFunction with 4:", someFunction(4)) } Run
  17. Flow control : if else package main import ( "fmt"

    "math/rand" "time" ) func main() { rand.Seed(time.Now().Unix()) i := rand.Intn(1e7) fmt.Println("i:", i) if i%2 == 0 { fmt.Println("i even") } else { fmt.Println("i is odd") } } Run
  18. Flow control : switch package main import ( "fmt" "math/rand"

    "time" ) func main() { rand.Seed(time.Now().Unix()) i := rand.Intn(1e6 + 1) fmt.Println("i:", i) switch { case i > 1 && i < 1000: fmt.Println("Between one and thousand") case i > 1000 && i < 1e6: fmt.Println("Between hundred and 1 million") default: fmt.Println("Too huge ! Lucky guy :)") } } Run
  19. Flow control : for package main import ( "fmt" "math/rand"

    "time" ) func main() { rand.Seed(time.Now().Unix()) i := rand.Intn(20) for index := 0; index < i; index++ { fmt.Println("Index:", index) } } Run
  20. Array/Slices package main import ( "fmt" "math/rand" "time" ) func

    main() { ciphers := [...]byte{0, 1, 2, 3, 4, 5, 6, 7, 8, 9} fmt.Println("Ciphers:", ciphers) fmt.Println("Slice 1:", ciphers[5:]) fmt.Println("Slice 2:", ciphers[:5]) fmt.Println("Slice 3:", ciphers[1:5]) rand.Seed(time.Now().Unix()) table := make([]int, 10) for index, _ := range table { table[index] = rand.Intn(100) } fmt.Println("Table:", table) } Run
  21. Map package main import ( "fmt" ) func main() {

    data := map[string]int{ "key1": 31, "key2": 28, "key3": 24, } for key, value := range data { fmt.Printf("Key %s: %d\n", key, value) } } Run
  22. Dependencies managed with packages //Package module func Square(n int) int

    { return n * n } //Private to package because of 's' (lowercase) func pow3(n int) int { return Square(n) * n } package main import ( "fmt" "module" ) func main() { //OK fmt.Println("Square 3", module.Square(3)) //ERROR fmt.Println("pow 3", module.pow3(3)) }
  23. Retrieve external dependencies import ( "github.com/pmylund/go-cache" "launchpad.net/gnuflag" "bitbucket.org/taruti/ssh.go" "code.google.com/p/go-avltree" )

    $ go get [import] Retrieves automatically code from GitHub, Bitbucket, Launchpad, Google code (until it dies)
  24. Error management package main import ( "log" "net/http" ) func

    main() { _, err := http.Get("https://www.openwwdwedwedt.com/") if err != nil { log.Fatal(err) } } Run
  25. Deferring package main import ( "io/ioutil" "log" "net/http" ) func

    main() { res, err := http.Get("https://www.openwt.com/") if err != nil { log.Fatal(err) } defer res.Body.Close() data, err := ioutil.ReadAll(res.Body) if err != nil { log.Fatal(err) } log.Println("HTML:", string(data)) } Run
  26. Closures package main import ( "log" ) func multiplicator(n int)

    func(int) int { return func(number int) int { return n * number } } func main() { ten := multiplicator(10) two := multiplicator(2) log.Println("16 times 10:", ten(16)) log.Println("45 times 2:", two(45)) } Run
  27. Custom type package main import ( "fmt" ) type Person

    struct { Name string } func (p *Person) presenting() { fmt.Printf("Hello, I'm %s\n", p.Name) } func main() { a := Person{Name: "Georges"} a.presenting() } Run
  28. Custom type package main import ( "fmt" ) type Person

    struct { Name string } func (p Person) changeName(name string) { p.Name = name } func main() { a := Person{Name: "Georges"} b := &Person{Name: "Martin"} a.changeName("Justin") b.changeName("Justin") fmt.Println("A:", a) fmt.Println("B:", b) } Run
  29. Composition over inheritance package main import "fmt" type AccessLevel int

    type User struct { Login string Password string } type Administrator struct { User User Level AccessLevel } const ( Nothing AccessLevel = iota God ) func main() { admin := &Administrator{Level: God, User: User{Login: "su", Password: "3.1419527"}} fmt.Println("Admin:", admin) } Run
  30. package main import "fmt" type Employee struct { Name string

    } type Boss struct { Employee } func (e *Employee) Work() { fmt.Println("Work Hard") } func (e *Employee) FillTimeSheet() { fmt.Println("I fill my time sheet as", e.Name) } func (b *Boss) Work() { b.Employee.Work() fmt.Println("Chilling :)") } func main() { boss := &Boss{Employee: Employee{"God"}} boss.FillTimeSheet() boss.Work() } Run
  31. Interface and Duck typing When I see a bird that

    walks like a duck and swims like a duck and quacks like a duck, I call that bird a duck James Whitcomb Riley Go deals with polymorphism through the concept of interface If a struct implements all the methods de ned in the interface, it is compatible with it No coupling between foreign packages Interface should be considered as pointer
  32. package main import "fmt" type Animal interface { Noise() string

    } type Dog struct{} func (d *Dog) Noise() string { return "waf" } type Cat struct{} func (c Cat) Noise() string { return "miaou" } func main() { var animalA Animal = &Dog{} var animalB Animal = Cat{} fmt.Println("Animal A:", animalA.Noise()) fmt.Println("Animal B:", animalB.Noise()) } Run
  33. Dynamic type checking package main import ( "fmt" ) type

    Count int func main() { values := []interface{}{1, "fwefwefw", Count(9)} for _, value := range values { switch value.(type) { case int: fmt.Printf("Value is a int %d\n", value) case string: fmt.Printf("Is a string:%s\n", value) case Count: fmt.Printf("Is a Count:%d\n", value) } } } Run
  34. Type assertion package main import ( "fmt" ) func main()

    { var unknown interface{} = 2 _, ok := unknown.(string) if ok { fmt.Println("Is a string") } else { fmt.Println("Is not a string :(") } } Run
  35. Concurrency Concurrency is not parallelism Synchronisation based on CSP (http://spinroot.com/courses/summer/Papers/hoare_1978.pdf)

    (like Erlang, Rust, Akka in Scala) Use kind of Green Threads mapped on OS threads called goroutine Simply call go
  36. Goroutine package main import ( "fmt" "time" ) func work(n

    time.Duration) { time.Sleep(n * time.Millisecond) fmt.Printf("%d ms\n", n) } func main() { go work(400) go work(200) work(1000) } Run
  37. Channel package main import ( "fmt" "time" ) func work(ch

    chan bool, n time.Duration) { time.Sleep(n * time.Millisecond) fmt.Printf("%d ms\n", n) ch <- true } func main() { ch := make(chan bool) go work(ch, 1000) go work(ch, 600) go work(ch, 300) <-ch <-ch <-ch fmt.Println("Finished!") } Run
  38. Channel package main import ( "fmt" ) func intGenerator() chan

    int { ch := make(chan int) id := 0 go func() { for { ch <- id id++ } }() return ch } func main() { generator := intGenerator() fmt.Println("Int:", <-generator) fmt.Println("Int:", <-generator) fmt.Println("Int:", <-generator) } Run
  39. Select package main import ( "fmt" "time" ) func longWork()

    bool { time.Sleep(3 * time.Millisecond) return true } func main() { timeout := time.After(1 * time.Millisecond) ch := make(chan bool) go func() { ch <- longWork() }() select { case <-ch: fmt.Println("Long work finished....") case <-timeout: fmt.Println("Timeout...") } } Run
  40. The standard library covers almost everything SQL Database Syscall TCP/IP,

    FTP, HTTP, SMTP, JSON, XML, HTML, templating, CSV Unicode Image processing Crypto: RSA, AES, DES, SHA, TLS, x509 Compression: bz2, gz, lzw, zip Math Go AST, debug, sytax Re ection (introspection) Testing framework (assertions)
  41. And a free swissknife A list of helpers tool (non

    exhaustive): - Format: fmt - Documentation: doc - Pro ling: pprof - Code coverage: gcov - YACC clone: yacc - Migrations: x
  42. Libraries Awesome go (https://github.com/avelino/awesome-go) Full Stack Web frameworks: Beego, Revel,

    Martini (Re ection) HTTP Midlewares based framework: negroni Abuse of HTTP middlewares My recommandation to start : pat (https://github.com/bmizerany/pat) (muxer), negroni (https://github.com/codegangsta/negroni) (HTTP middlewares) and gorilla (www.gorillatoolkit.org/) packages (context, sessions)
  43. Some awesome Go projects Docker (https://docker.io) : An open platform

    for distributed applications for developers and sysadmins hugo (http://gohugo.io/) : A Fast and Modern Static Website Engine limetext (http://limetext.org/) : Lime Text is a powerful and elegant text editor primarily developed in Go that aims to be a Free and open-source software successor to Sublime Text. nes (https://github.com/fogleman/nes) : A Nintendo Entertainment System (NES) emulator written in Go bolt (https://github.com/boltdb/bolt) : A low-level key/value database for Go. cayley (https://github.com/google/cayley) : A graph database with support for multiple backends.
  44. Conclusion Abuse of Go ! Supported by Heroku, Scalingo, Redshift,

    GAE... Start the Go Tour: tour.golang.org (http://tour.golang.org) See the Go Codewalks: golang.org/doc/codewalk/ (https://golang.org/doc/codewalk/)
  45. References The bible, coran and torah: golang.org (http://golang.org) The Go

    blog: blog.golang.com (http://blog.golang.com) Main GoDoc server: godoc.org (https://godoc.org) Google: search for golang
  46. People to follow: Rob Pike, Go Team Lead - @rob_pike

    (https://twitter.com/rob_pike) Francesc Compoy, Go Evangelist - @francesc (https://twitter.com/francesc) Jessie Frazelle, Docker developer - @frazelledazzell (https://twitter.com/frazelledazzell) Jeremy Saenz, martini, negroni developer - @codegangsta (https://twitter.com/codegangsta)
  47. Thank you Yannick Heinrich Software Developer, OpenWeb Technology [email protected] (mailto:[email protected])

    http://blog.yageek.net (http://blog.yageek.net) @yageek (http://twitter.com/yageek)