From a11a0343559e55e07c13b0c800c5e3ff1a53f6dc Mon Sep 17 00:00:00 2001 From: Antonio De Lucreziis Date: Sun, 2 Apr 2023 01:57:02 +0200 Subject: [PATCH] Tolti esempi prototipo --- examples/001-generic-methods/cons_test.go | 60 -------- examples/001-generic-methods/http_test.go | 134 ------------------ examples/001-generic-methods/min_test.go | 31 ---- examples/001-generic-methods/stack_test.go | 29 ---- examples/002-refs/main.go | 99 ------------- examples/003-adt/main.go | 49 ------- examples/004-gadt/main.go | 45 ------ .../005-iface-vs-typeparam/example5_test.go | 61 -------- 8 files changed, 508 deletions(-) delete mode 100644 examples/001-generic-methods/cons_test.go delete mode 100644 examples/001-generic-methods/http_test.go delete mode 100644 examples/001-generic-methods/min_test.go delete mode 100644 examples/001-generic-methods/stack_test.go delete mode 100644 examples/002-refs/main.go delete mode 100644 examples/003-adt/main.go delete mode 100644 examples/004-gadt/main.go delete mode 100644 examples/005-iface-vs-typeparam/example5_test.go diff --git a/examples/001-generic-methods/cons_test.go b/examples/001-generic-methods/cons_test.go deleted file mode 100644 index ecaa51b..0000000 --- a/examples/001-generic-methods/cons_test.go +++ /dev/null @@ -1,60 +0,0 @@ -package genericmethods_test - -type Cons[L, R any] struct { - Left L - Right L -} - -// interface cast type check -func _[T any]() LiftLower[BoxT, T] { return &Box[T]{} } - -type BoxT struct{} -type Box[T any] struct { - Content T -} - -func (c Box[T]) Lift() V[BoxT, T] { - return c -} -func (c *Box[T]) Lower(v V[BoxT, T]) { - *c = v.(Box[T]) -} - -// interface cast type check -func _[T any]() LiftLower[ChestT, T] { return &Chest[T]{} } - -type ChestT struct{} -type Chest[T any] struct { - Treasure T -} - -func (c Chest[T]) Lift() V[ChestT, T] { - return c -} -func (c *Chest[T]) Lower(v V[ChestT, T]) { - *c = v.(Chest[T]) -} - -type LiftLower[F ~struct{}, T any] interface { - Lift() V[F, T] - Lower(v V[F, T]) -} - -func BoxToChest[T any](b Box[T]) Chest[T] { - return Chest[T]{b.Content} -} - -func BoxToChestLifted[T any](b V[BoxT, T]) V[ChestT, T] { - var bb Box[T] - bb.Lower(b) - return Chest[T]{bb.Content}.Lift() -} - -type V[F ~struct{}, T any] any - -type ConsF[F, T, R any] struct{} - -func _() { - // l1 := Cons[Box[int], Box[string]]{} - -} diff --git a/examples/001-generic-methods/http_test.go b/examples/001-generic-methods/http_test.go deleted file mode 100644 index 00c4089..0000000 --- a/examples/001-generic-methods/http_test.go +++ /dev/null @@ -1,134 +0,0 @@ -package genericmethods_test - -import ( - "database/sql" - "encoding/json" - "fmt" - "net/http" - "strings" - "testing" -) - -type Validator interface { - Validate() error -} - -type FooRequest struct { - A int `json:"a"` - B string `json:"b"` -} - -func (foo FooRequest) Validate() error { - if foo.A < 0 { - return fmt.Errorf(`parameter "a" cannot be lesser than zero`) - } - if !strings.HasPrefix(foo.B, "baz-") { - return fmt.Errorf(`parameter "b" has wrong prefix`) - } - - return nil -} - -func DecodeAndValidateJSON_Generic[T Validator](r *http.Request) (T, error) { - var value T - err := json.NewDecoder(r.Body).Decode(&value) - if err != nil { - var zero T - return zero, err - } - - if err := value.Validate(); err != nil { - var zero T - return zero, err - } - - return value, nil -} - -func TestDecodeAndValidateJSON_Generic(t *testing.T) { - m := http.NewServeMux() - m.HandleFunc("/foo", func(w http.ResponseWriter, r *http.Request) { - foo, err := DecodeAndValidateJSON_Generic[FooRequest](r) - if err != nil { - http.Error(w, err.Error(), http.StatusInternalServerError) - return - } - - json.NewEncoder(w).Encode(foo) - }) -} - -func DecodeAndValidateJSON_Interface(r *http.Request, target *Validator) error { - err := json.NewDecoder(r.Body).Decode(target) - if err != nil { - return err - } - - if err := (*target).Validate(); err != nil { - return err - } - - return nil -} - -func TestDecodeAndValidateJSON_Interface(t *testing.T) { - m := http.NewServeMux() - m.HandleFunc("/foo", func(w http.ResponseWriter, r *http.Request) { - var foo Validator = FooRequest{} - if err := DecodeAndValidateJSON_Interface(r, &foo); err != nil { - http.Error(w, err.Error(), http.StatusInternalServerError) - return - } - - json.NewEncoder(w).Encode(foo) - }) -} - -type WithPrimaryKey interface { - PrimaryKeyPtr() *string -} - -type Ref[T WithPrimaryKey] string - -type Table[T WithPrimaryKey] struct { - Name string - PkColumn string -} - -func IdToRef[T WithPrimaryKey](table Table[T], id string) (Ref[T], error) { - if !strings.HasPrefix(id, table.Name+":") { - var zero Ref[T] - return zero, fmt.Errorf(`invalid reference %v for table %v`, id, table) - } - - return Ref[T](id), nil -} - -func Read[T WithPrimaryKey](db *sql.DB, table Table[T], ref Ref[T]) (*T, error) { - result := db.QueryRow( - fmt.Sprintf( - `SELECT * FROM %s WHERE %s = ?`, - table.Name, table.PkColumn, - ), - string(ref), - ) - - var value T - if err := result.Scan(&value); err != nil { - return nil, err - } - - return &value, nil -} - -type User struct { - Username string - FirstName string - LastName string -} - -var _ WithPrimaryKey = &User{} - -func (u *User) PrimaryKeyPtr() *string { - return &u.Username -} diff --git a/examples/001-generic-methods/min_test.go b/examples/001-generic-methods/min_test.go deleted file mode 100644 index 84705be..0000000 --- a/examples/001-generic-methods/min_test.go +++ /dev/null @@ -1,31 +0,0 @@ -package genericmethods_test - -import ( - "testing" - - "golang.org/x/exp/constraints" -) - -func Min[T constraints.Ordered](x, y T) T { - if x < y { - return x - } - return y -} - -type Liter int - -func TestInt(t *testing.T) { - { - var a, b int = 1, 2 - Min(a, b) - } - { - var a, b float64 = 3.14, 2.71 - Min(a, b) - } - { - var a, b Liter = 1, 2 - Min(a, b) - } -} diff --git a/examples/001-generic-methods/stack_test.go b/examples/001-generic-methods/stack_test.go deleted file mode 100644 index e182054..0000000 --- a/examples/001-generic-methods/stack_test.go +++ /dev/null @@ -1,29 +0,0 @@ -package genericmethods_test - -type Stack[T any] []T - -func (s *Stack[T]) Push(value T) { - *s = append(*s, value) -} - -func (s Stack[T]) Peek() T { - return s[len(s)-1] -} - -func (s Stack[T]) Len() int { - return len(s) -} - -func (s *Stack[T]) Pop() (T, bool) { - items := *s - - if len(items) == 0 { - var zero T - return zero, false - } - - newStack, poppedValue := items[:len(items)-1], items[len(items)-1] - *s = newStack - - return poppedValue, true -} diff --git a/examples/002-refs/main.go b/examples/002-refs/main.go deleted file mode 100644 index 94db246..0000000 --- a/examples/002-refs/main.go +++ /dev/null @@ -1,99 +0,0 @@ -package main - -import ( - "fmt" - "log" -) - -// -// Database -// - -type QueryResult interface { - Scan(v any) error -} - -type Database interface { - Get(query string, values ...any) QueryResult -} - -// -// Library -// - -// DatabaseTable represents a typed database table with -type DatabaseTable[T any] struct { - Table string - IdKey string - GetIdPtr func(entry T) *string -} - -func (t DatabaseTable[T]) RefForId(id string) DatabaseRef[T] { - return DatabaseRef[T]{id} -} - -func (t DatabaseTable[T]) RefForValue(v T) DatabaseRef[T] { - return t.RefForId(*t.GetIdPtr(v)) -} - -type DatabaseRef[T any] struct{ Id string } - -func DatabaseRead[T any](db Database, table DatabaseTable[T], ref DatabaseRef[T]) (*T, error) { - query := fmt.Sprintf(`select * from %s where %s = ?`, table.Table, table.IdKey) - - result := db.Get(query, ref.Id) - - var value T - if err := result.Scan(&value); err != nil { - return nil, err - } - - return &value, nil -} - -// DatabaseWrite creates a new entry in the db using the provided id in the value, this returns a typed ref to the db entry -func DatabaseWrite[T any](db Database, table DatabaseTable[T], value *T) (DatabaseRef[T], error) { - panic("not implemented") -} - -// DatabaseCreate creates a new entry in the db retrieving the new generated id and returning it as a typed ref -func DatabaseCreate[T any](db Database, table DatabaseTable[T], value *T) (DatabaseRef[T], error) { - panic("not implemented") -} - -// -// Client code -// - -type User struct { - Username string - FirstName string - LastName string -} - -var UsersTable = DatabaseTable[User]{ - Table: "users", - IdKey: "username", - GetIdPtr: func(u User) *string { - return &u.Username - }, -} - -func _(db Database) error { - u1 := &User{"j.smith", "John", "Smith"} - log.Println(u1) - - ref1, err := DatabaseWrite(db, UsersTable, u1) - if err != nil { - return err - } - - u2, err := DatabaseRead(db, UsersTable, ref1) - if err != nil { - return err - } - - log.Println(u2) - - return nil -} diff --git a/examples/003-adt/main.go b/examples/003-adt/main.go deleted file mode 100644 index f956368..0000000 --- a/examples/003-adt/main.go +++ /dev/null @@ -1,49 +0,0 @@ -package main - -// type Option[T] = Some(T) | None - -type Option[T any] interface { - Match( - caseSome func(value T), - caseNone func(), - ) -} - -type Some[T any] struct{ Value T } - -func (v Some[T]) Match(caseSome func(value T), caseNone func()) { - caseSome(v.Value) -} - -type None[T any] struct{} - -func (v None[T]) Match(caseSome func(value T), caseNone func()) { - caseNone() -} - -// type Either[A, B] = Left A | Right B - -type Either[A, B any] interface { - Match( - caseLeft func(value A), - caseRight func(value B), - ) -} - -type Left[A, B any] struct{ Value A } - -func (v Left[A, B]) Match( - caseLeft func(value A), - caseRight func(value B), -) { - caseLeft(v.Value) -} - -type Right[A, B any] struct{ Value B } - -func (v Right[A, B]) Match( - caseLeft func(value A), - caseRight func(value B), -) { - caseRight(v.Value) -} diff --git a/examples/004-gadt/main.go b/examples/004-gadt/main.go deleted file mode 100644 index eaf8149..0000000 --- a/examples/004-gadt/main.go +++ /dev/null @@ -1,45 +0,0 @@ -package main - -type Expr[T any] interface{} - -func Match() { - -} - -type numExpr struct { - value int -} - -func Num(value int) Expr[int] { - return &numExpr{value} -} - -type sumExpr struct { - lhs, rhs Expr[int] -} - -func Sum(lhs, rhs Expr[int]) Expr[int] { - return &sumExpr{lhs, rhs} -} - -type leqExpr struct { - lhs, rhs Expr[int] -} - -func Leq(lhs, rhs Expr[int]) Expr[bool] { - return &leqExpr{lhs, rhs} -} - -type ifExpr[R any] struct { - cond Expr[bool] - ifTrue Expr[R] - ifFalse Expr[R] -} - -func If[R any](cond Expr[bool], ifTrue Expr[R], ifFalse Expr[R]) Expr[R] { - return &ifExpr[R]{cond, ifTrue, ifFalse} -} - -func main() { - -} diff --git a/examples/005-iface-vs-typeparam/example5_test.go b/examples/005-iface-vs-typeparam/example5_test.go deleted file mode 100644 index 61a793a..0000000 --- a/examples/005-iface-vs-typeparam/example5_test.go +++ /dev/null @@ -1,61 +0,0 @@ -package example5_test - -import ( - "bytes" - "io" - "testing" -) - -func WriteSingleWithInterface(w io.Writer, data byte) { - w.Write([]byte{data}) -} - -//go:noinline -func WriteSingleWithInterfaceNoInline(w io.Writer, data byte) { - w.Write([]byte{data}) -} - -func WriteSingleWithGeneric[T io.Writer](w T, data byte) { - w.Write([]byte{data}) -} - -//go:noinline -func WriteSingleWithGenericNoInline[T io.Writer](w T, data byte) { - w.Write([]byte{data}) -} - -func Test1(t *testing.T) { - t.Log(`Ok!`) -} - -func BenchmarkInterface(b *testing.B) { - d := &bytes.Buffer{} - - for i := 0; i < b.N; i++ { - WriteSingleWithInterface(d, 42) - } -} - -func BenchmarkInterfaceNoInline(b *testing.B) { - d := &bytes.Buffer{} - - for i := 0; i < b.N; i++ { - WriteSingleWithInterfaceNoInline(d, 42) - } -} - -func BenchmarkGeneric(b *testing.B) { - d := &bytes.Buffer{} - - for i := 0; i < b.N; i++ { - WriteSingleWithGeneric(d, 42) - } -} - -func BenchmarkGenericNoInline(b *testing.B) { - d := &bytes.Buffer{} - - for i := 0; i < b.N; i++ { - WriteSingleWithGenericNoInline(d, 42) - } -}