mirror of
https://github.com/IBM/fp-go.git
synced 2025-08-10 22:31:32 +02:00
doc: add examples and solutions from mostly adequate
Signed-off-by: Dr. Carsten Leue <carsten.leue@de.ibm.com>
This commit is contained in:
@@ -24,3 +24,9 @@ func MagmaSub[A Number]() M.Magma[A] {
|
|||||||
return first - second
|
return first - second
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func MagmaDiv[A Number]() M.Magma[A] {
|
||||||
|
return M.MakeMagma(func(first A, second A) A {
|
||||||
|
return first / second
|
||||||
|
})
|
||||||
|
}
|
||||||
|
@@ -19,6 +19,7 @@ import (
|
|||||||
M "github.com/IBM/fp-go/monoid"
|
M "github.com/IBM/fp-go/monoid"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// MonoidSum is the [Monoid] that adds elements with a zero empty element
|
||||||
func MonoidSum[A Number]() M.Monoid[A] {
|
func MonoidSum[A Number]() M.Monoid[A] {
|
||||||
s := SemigroupSum[A]()
|
s := SemigroupSum[A]()
|
||||||
return M.MakeMonoid(
|
return M.MakeMonoid(
|
||||||
@@ -26,3 +27,12 @@ func MonoidSum[A Number]() M.Monoid[A] {
|
|||||||
0,
|
0,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// MonoidProduct is the [Monoid] that multiplies elements with a one empty element
|
||||||
|
func MonoidProduct[A Number]() M.Monoid[A] {
|
||||||
|
s := SemigroupProduct[A]()
|
||||||
|
return M.MakeMonoid(
|
||||||
|
s.Concat,
|
||||||
|
1,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
@@ -24,3 +24,9 @@ func SemigroupSum[A Number]() S.Semigroup[A] {
|
|||||||
return first + second
|
return first + second
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func SemigroupProduct[A Number]() S.Semigroup[A] {
|
||||||
|
return S.MakeSemigroup(func(first A, second A) A {
|
||||||
|
return first * second
|
||||||
|
})
|
||||||
|
}
|
||||||
|
@@ -24,16 +24,30 @@ type Number interface {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Add is a curried function used to add two numbers
|
// Add is a curried function used to add two numbers
|
||||||
func Add[T Number](left T) func(T) T {
|
func Add[T Number](right T) func(T) T {
|
||||||
return func(right T) T {
|
return func(left T) T {
|
||||||
return left + right
|
return left + right
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Mul is a curried function used to add two numbers
|
// Sub is a curried function used to subtract two numbers
|
||||||
func Mul[T Number](coeff T) func(T) T {
|
func Sub[T Number](right T) func(T) T {
|
||||||
return func(value T) T {
|
return func(left T) T {
|
||||||
return coeff * value
|
return left - right
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Mul is a curried function used to multiply two numbers
|
||||||
|
func Mul[T Number](right T) func(T) T {
|
||||||
|
return func(left T) T {
|
||||||
|
return left * right
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Div is a curried function used to divide two numbers
|
||||||
|
func Div[T Number](right T) func(T) T {
|
||||||
|
return func(left T) T {
|
||||||
|
return left / right
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -0,0 +1,38 @@
|
|||||||
|
// Copyright (c) 2023 IBM Corp.
|
||||||
|
// All rights reserved.
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
package mostlyadequate
|
||||||
|
|
||||||
|
import "fmt"
|
||||||
|
|
||||||
|
func Hi(name string) string {
|
||||||
|
return fmt.Sprintf("Hi %s", name)
|
||||||
|
}
|
||||||
|
|
||||||
|
func Greeting(name string) string {
|
||||||
|
return Hi(name)
|
||||||
|
}
|
||||||
|
|
||||||
|
func Example_greeting() {
|
||||||
|
// functions are first class objects
|
||||||
|
greet := Hi
|
||||||
|
|
||||||
|
fmt.Println(Greeting("times"))
|
||||||
|
fmt.Println(greet("times"))
|
||||||
|
|
||||||
|
// Output:
|
||||||
|
// Hi times
|
||||||
|
// Hi times
|
||||||
|
}
|
@@ -16,9 +16,12 @@
|
|||||||
package mostlyadequate
|
package mostlyadequate
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"fmt"
|
||||||
|
"math"
|
||||||
"regexp"
|
"regexp"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
||||||
|
A "github.com/IBM/fp-go/array"
|
||||||
F "github.com/IBM/fp-go/function"
|
F "github.com/IBM/fp-go/function"
|
||||||
N "github.com/IBM/fp-go/number"
|
N "github.com/IBM/fp-go/number"
|
||||||
I "github.com/IBM/fp-go/number/integer"
|
I "github.com/IBM/fp-go/number/integer"
|
||||||
@@ -26,8 +29,9 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
Match = F.Curry2((*regexp.Regexp).FindStringSubmatch)
|
Match = F.Curry2((*regexp.Regexp).FindStringSubmatch)
|
||||||
Split = F.Curry2(F.Bind3of3((*regexp.Regexp).Split)(-1))
|
Matches = F.Curry2((*regexp.Regexp).MatchString)
|
||||||
|
Split = F.Curry2(F.Bind3of3((*regexp.Regexp).Split)(-1))
|
||||||
|
|
||||||
Add = N.Add[int]
|
Add = N.Add[int]
|
||||||
ToString = I.ToString
|
ToString = I.ToString
|
||||||
@@ -44,3 +48,36 @@ func Replace(search *regexp.Regexp) func(replace string) func(s string) string {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func Example_solution04A() {
|
||||||
|
// words :: String -> [String]
|
||||||
|
words := Split(regexp.MustCompile(` `))
|
||||||
|
|
||||||
|
fmt.Println(words("Jingle bells Batman smells"))
|
||||||
|
|
||||||
|
// Output:
|
||||||
|
// [Jingle bells Batman smells]
|
||||||
|
}
|
||||||
|
|
||||||
|
func Example_solution04B() {
|
||||||
|
// filterQs :: [String] -> [String]
|
||||||
|
filterQs := A.Filter(Matches(regexp.MustCompile(`q`)))
|
||||||
|
|
||||||
|
fmt.Println(filterQs(A.From("quick", "camels", "quarry", "over", "quails")))
|
||||||
|
|
||||||
|
// Output:
|
||||||
|
// [quick quarry quails]
|
||||||
|
}
|
||||||
|
|
||||||
|
func Example_solution04C() {
|
||||||
|
|
||||||
|
keepHighest := N.Max[int]
|
||||||
|
|
||||||
|
// max :: [Number] -> Number
|
||||||
|
max := A.Reduce(keepHighest, math.MinInt)
|
||||||
|
|
||||||
|
fmt.Println(max(A.From(323, 523, 554, 123, 5234)))
|
||||||
|
|
||||||
|
// Output:
|
||||||
|
// 5234
|
||||||
|
}
|
||||||
|
@@ -21,6 +21,9 @@ import (
|
|||||||
|
|
||||||
A "github.com/IBM/fp-go/array"
|
A "github.com/IBM/fp-go/array"
|
||||||
F "github.com/IBM/fp-go/function"
|
F "github.com/IBM/fp-go/function"
|
||||||
|
I "github.com/IBM/fp-go/number/integer"
|
||||||
|
O "github.com/IBM/fp-go/option"
|
||||||
|
"github.com/IBM/fp-go/ord"
|
||||||
S "github.com/IBM/fp-go/string"
|
S "github.com/IBM/fp-go/string"
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -58,3 +61,50 @@ func Example_pipe() {
|
|||||||
|
|
||||||
// Output: SEND IN THE CLOWNS!
|
// Output: SEND IN THE CLOWNS!
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func Example_solution05A() {
|
||||||
|
IsLastInStock := F.Flow2(
|
||||||
|
A.Last[Car],
|
||||||
|
O.Map(Car.getInStock),
|
||||||
|
)
|
||||||
|
|
||||||
|
fmt.Println(IsLastInStock(Cars[0:3]))
|
||||||
|
fmt.Println(IsLastInStock(Cars[3:]))
|
||||||
|
|
||||||
|
// Output:
|
||||||
|
// Some[bool](true)
|
||||||
|
// Some[bool](false)
|
||||||
|
}
|
||||||
|
|
||||||
|
func Example_solution05B() {
|
||||||
|
// averageDollarValue :: [Car] -> Int
|
||||||
|
averageDollarValue := F.Flow2(
|
||||||
|
A.Map(Car.getDollarValue),
|
||||||
|
average,
|
||||||
|
)
|
||||||
|
|
||||||
|
fmt.Println(averageDollarValue(Cars))
|
||||||
|
|
||||||
|
// Output:
|
||||||
|
// 790700
|
||||||
|
}
|
||||||
|
|
||||||
|
func Example_solution05C() {
|
||||||
|
// order by horsepower
|
||||||
|
ordByHorsepower := ord.Contramap(Car.getHorsepower)(I.Ord)
|
||||||
|
|
||||||
|
// fastestCar :: [Car] -> Option[String]
|
||||||
|
fastestCar := F.Flow3(
|
||||||
|
A.Sort(ordByHorsepower),
|
||||||
|
A.Last[Car],
|
||||||
|
O.Map(F.Flow2(
|
||||||
|
Car.getName,
|
||||||
|
S.Format[string]("%s is the fastest"),
|
||||||
|
)),
|
||||||
|
)
|
||||||
|
|
||||||
|
fmt.Println(fastestCar(Cars))
|
||||||
|
|
||||||
|
// Output:
|
||||||
|
// Some[string](Aston Martin One-77 is the fastest)
|
||||||
|
}
|
||||||
|
89
samples/mostly-adequate/support.go
Normal file
89
samples/mostly-adequate/support.go
Normal file
@@ -0,0 +1,89 @@
|
|||||||
|
// Copyright (c) 2023 IBM Corp.
|
||||||
|
// All rights reserved.
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
package mostlyadequate
|
||||||
|
|
||||||
|
import (
|
||||||
|
A "github.com/IBM/fp-go/array"
|
||||||
|
F "github.com/IBM/fp-go/function"
|
||||||
|
N "github.com/IBM/fp-go/number"
|
||||||
|
)
|
||||||
|
|
||||||
|
type (
|
||||||
|
Car struct {
|
||||||
|
Name string
|
||||||
|
Horsepower int
|
||||||
|
DollarValue float32
|
||||||
|
InStock bool
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
func (car Car) getInStock() bool {
|
||||||
|
return car.InStock
|
||||||
|
}
|
||||||
|
|
||||||
|
func (car Car) getDollarValue() float32 {
|
||||||
|
return car.DollarValue
|
||||||
|
}
|
||||||
|
|
||||||
|
func (car Car) getHorsepower() int {
|
||||||
|
return car.Horsepower
|
||||||
|
}
|
||||||
|
|
||||||
|
func (car Car) getName() string {
|
||||||
|
return car.Name
|
||||||
|
}
|
||||||
|
|
||||||
|
func average(val []float32) float32 {
|
||||||
|
return F.Pipe2(
|
||||||
|
val,
|
||||||
|
A.Fold(N.MonoidSum[float32]()),
|
||||||
|
N.Div(float32(len(val))),
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
var (
|
||||||
|
Cars = A.From(Car{
|
||||||
|
Name: "Ferrari FF",
|
||||||
|
Horsepower: 660,
|
||||||
|
DollarValue: 700000,
|
||||||
|
InStock: true,
|
||||||
|
}, Car{
|
||||||
|
Name: "Spyker C12 Zagato",
|
||||||
|
Horsepower: 650,
|
||||||
|
DollarValue: 648000,
|
||||||
|
InStock: false,
|
||||||
|
}, Car{
|
||||||
|
Name: "Jaguar XKR-S",
|
||||||
|
Horsepower: 550,
|
||||||
|
DollarValue: 132000,
|
||||||
|
InStock: true,
|
||||||
|
}, Car{
|
||||||
|
Name: "Audi R8",
|
||||||
|
Horsepower: 525,
|
||||||
|
DollarValue: 114200,
|
||||||
|
InStock: false,
|
||||||
|
}, Car{
|
||||||
|
Name: "Aston Martin One-77",
|
||||||
|
Horsepower: 750,
|
||||||
|
DollarValue: 1850000,
|
||||||
|
InStock: true,
|
||||||
|
}, Car{
|
||||||
|
Name: "Pagani Huayra",
|
||||||
|
Horsepower: 700,
|
||||||
|
DollarValue: 1300000,
|
||||||
|
InStock: false,
|
||||||
|
})
|
||||||
|
)
|
Reference in New Issue
Block a user