Notes on the Go Programming Langugae

Some notes on the Go programming language that I took by watching youtube videos, reading / skimming through a textbook, and reading a README on github. Just an introduction to the language. I want to learn Go because the things that I want to implement in future projects cannot be implemented with the quality that I want with a Node.js backend. As my first project with Go, I plan to try to convert the backend for this website to Go.

Go Notes

Go Notes Using Youtube

I'm using this youtube video to lean about GO.

Go Introduction

Setting Up Project

Constants Variables and Data Types

Functions and Control Structures

Arrays, Slices, Maps, Loops

var i int = 0
for i < 10 {
  fmt.Println(i)
  i = i+1
}
for i:=0; i <10; i++ {
        fmt.Println(i)
}

Strings

Structs and Interfaces

Pointers and How They are Used in GO

Go Routines

Channels And Go Routines

Generics

func genericSumSlice[T int | float32 | float64](slice []T) T {
    var sum T 
    for _, v := range slice {
        sum+=v
    }
    return sum
}

General

The Go Programming Language, Alan Donovan, Brian W. Kernighan

Chapter 1: Tutorial

for initialization; condition; post {
  // zero or more statements
}
s := ""
var s string

Chapter 2: Program Structure

Declarations

Variables

var name = type expression

Short Variable Declarations

Pointers

x := 1
p := &x // p, of type *int, points to x 
fmt.Println(*p) // "l"
*p = 2 // equivalent to x = 2
fmt.Println(x) // "2"

Lifetime of Variables

Assignments

func example() {
  x := 1
  y := 2
  k := 3
  // Tuple Assignment
  x, y, k = y, x, 5
}

Assignability

Type Declarations

Packages and Files

Scope

var cwd string;
func init() {
  // Short variable declaration declares local variable cwd, does not assign to package level variable cwd
  cwd, err := os.Getwd() // Compile error: unused: cwd
  if err != nil {
    log.Fatalf("od.Getwd failed: %v",err) 
  }
}

Chapter 3: Basic Data Types

Strings

// Enumeration / enum / iota Example (Can use iota in more complex ecpressions)
type Weekday int 
const (
    Sunday Weekday = iota // 0
    Monday // 1
    Tuesday // 2
    Wednesday 
    Thursday 
    Friday 
    Saturday
)

Chapter 4: Composite Types

Arrays and structs are aggregate types; their values are concatenations of other values in memory. Arrays are homogeneous - their elements have the same type - whereas structs are heterogeneous. Both arrays and structs are fixed size. In contrast, slices and maps are dynamic data structures that grow as values are added.

Arrays

var q = [3]int{1,2,3}
var r = [3]int{1,2} // 
fmt.Printf("%v",r[2]) // 0 -> Uninitialized array elements are initialized to the zero value for the type of each element of the array
var arr = [...]int{99:-1} // each value in this 100 length array has a value of the zero value for int (0) except for the last element, which is -1

Slices

Maps

Structs

JSON

Text and HTML Templates

Chapter 5: Functions

func name(parameter-list) (result-list) {
  body
}
func hypot(x, y float64) {
  return math.Sqrt(x*x + y*y)
}
fmt.Println(hypot(3,4)) // "5"
strings.Map(func(r rune) rune {
  return r+1, 
},"HAL-9000") // IBM.:111
func cum(vals ...int) int {
  total := 0
  for _, val := range vals {
    total += val
  }
  return total
}
func title(url string) error {
  resp, err := http.Get(url)
  if err != nil {
    return err
  }
  defer resp.Body.Close()
  ct := resp.Header.Get("Content-Type")
  if ct != "text/html" && ! strings.HasPrefix(ct,"text/html;") {
    return fmt.Errorf("%s has type %s, not text/html",url,ct)
  }
  doc, err := html.Parse(resp.Body)
  if err != nil {
    return fmt.Errorf("parsing %s as HTML: %v",url,err)
  }
  // ...print doc's title element
  return nil
}

Chapter 6: Methods

package geometry 
import "math"
type Point struct{ X, Y float64}
// traditional function 
func Distance(p, q Point) float64 {
  return math.Hypot(q.X-p.X,q.Y-p.Y)
}
// same thing, but as a method of the point type 
func (p Point) Distance(q Point) float64 {
  return math.Hypot(q.X-p.X,q.Y-p.Y)
}

Because calling a function makes a copy of each argument value, if a function needs to update a variable, or if an argument is so large that we wish to avoid copying it, we must pass address of the variable using a pointer. The same goes for methods that need to update the receiver variable, we attach them to the pointer type, such as *Point

func (p *Point) ScaleBy(factor float64) {
  p.X *= factor 
  p.Y *= factor
} 
p := Point{X: 2.5, Y: 2.5}
// ...
(*p).ScaleBy(2) 
fmt.Printf("%v",p) // {5,5}
// ...

Chapter 7: Interfaces

Interface types express generalizations or abstractions about the behaviors of other types. By generalizing, interfaces let us write functions that are more flexible and adaptable because they are not tied to the details of one particular implementation.

type Reader interface {
  Read(p []byte) (n int, err error)
}
type Closer interface {
  Close() error
}
type ReadWriter interface {
  Reader
  Writer
}
type ReadWriteCloser interface {
  Reader
  Writer
  Closer
}

Chapter 8: Goroutines and Channels

Concurrent programming, the expression of a program as a composition of several autonomous activities, has never been more important than it is today. Web servers handle requests for thousands of clients at once. Tablet and phone apps render animations in the user interface while simultaneously performing computation and network requests in the background. Even traditional batch problems—read some data, compute, write som e output—use concurrency to hide the latency of I/O operations and to exploit a modern computer’s many processors, which every year grow in number but not in speed.
This chapter presents goroutines and channels, which support communicating sequential processes or CSP, a model of concurrency in which values are passed between independent activities (goroutines) but variables are for the most part confined to a single activity. Chapter 9 covers some aspects of the more traditional model of shared memory multithreading, which will be familiar if you’ve used threads in other mainstream languages.

f() // call f(); wait for it to return
go f() // Create a new goroutine that calls f(); don't wait

If goroutines are the activities of a concurrent Go program, channels are the connections between them. A channel is a communication mechanism that lets one goroutine send values to another goroutine. Each channel is a conduit for values of a particular type, called the channel’s element type. The type of a channel whose elements have type int is written chan int.

ch := make(chan int) // ch has type 'chan int'
ch <- x // a send statement
x = <-ch // a receive statement in an assignment statement 
<-ch // a receive statement; result is discarded
close(ch)
ch = make(chan int) // unbuffered channel 
ch = make(chan int, 0) // unbuffered channel
ch = make(chan int, 3) // buffered channel with capacity 3

You needn’t close ever y channel when you’ve finished with it. It’s only necessary to close a channel when it is important to tell the receiving goroutines that all data have been sent.

Chapter 9: Concurrency with Shared Variables

A race condition is a situation in which the program does not give the correct result for some interleavings of the operations of multiple goroutines. Race conditions are pernicious because they may remain latent in a program and appear infrequently, perhaps only under heavy load or when using cer tain compilers, platforms, or architectures. This makes them hard to reproduce and diagnose.
We’ll rep eat the definition, since it is so important: A data race occurs whenever two goroutines access the same variable concurrently and at least one of the accesses is a write. It follows from this definition that there are three ways to avoid a data race.

Chapter 10: Packages and the Go tools

The only configuration most users ever need is the GOPATH environment variable, which specifies the root of the workspace. When switching to a different workspace, users update the value of GOPATH.

There was a lot to cover here. I didn't take as good of notes as I would have liked, but I will try to learn more about the Go language as I need to. I plan to rewrite the backend of this site in Go to make it faster and so that I can use Go for backend of different projects.

Standard Go Project Layout

Directories

/cmd

/internal

/pkg

/vendor

/api

OpenAPI.Swagger specs, JSON schema files, protocol definition files

/web - Web Application Directories

/config

/init

/scripts

/build

/deployments

/test

/docs

/tools

/examples

/third_party

/githooks

/assets

/website