• úvod
  • témata
  • události
  • tržiště
  • diskuze
  • nástěnka
  • přihlásit
    registrace
    ztracené heslo?
    BLAMIThe Go Programming Language - moderni programovaci jazyk
    BULHI
    BULHI --- ---
    RAGNAROK: no hele nevim, jestli tomu uplne rozumim, ale timhle tu funkci rovnou zavolas s tema parametrama a predavas pak jeji vystup
    func(10,"abc")


    takze bud teda parametry musis predat pri jejim volani a dostat je tam nejak jinak:
    
    func worker(task func(string)) {
        task("asdf")
    }
    
    printer := func(s string) {
        fmt.Println(s)
    }
    
    worker(printer)
    


    nebo pouzit closure, tj treba nejakej jakoby konstruktor, kde nastavis promenny, takze neco ve smyslu:
    
    func worker(task func()) {
        task()
    }
    
    func createPrinter(s string) func() {
        return func() {
            fmt.Println(s)
        }
    }
    
    printer1 := createPrinter("asdf")
    printer2 := createPrinter("qwerty")
    
    worker(printer1)
    worker(printer2)
    


    v Go ma anonymni funkce pristup k promennejm ve svym scope, coz je myslim stejne napriklad v Javascriptu, ale v PHP to myslim takhle nefunguje.. ale uz si teda nejsem jistej, nejak se mi to zacina plest :))
    RAGNAROK
    RAGNAROK --- ---
    Tady koukam na to jak pridavat joby do fronty.
    Job Queues in Go - OpsDash
    https://www.opsdash.com/blog/job-queues-in-go.html
    Tohle funguje dobre:
    
    func worker(jobChan <-chan func()) {
        for job := range jobChan {
            process(job)
        }
    }
    


    Akorat bych potreboval posilat funcke i s jejich prametrama na to nemuzu prijit jak. Ty parametry by meli mit hodnotu platnou prave v momente kdyz pridam job.
    Napr:.
    
    <-func(10,"abc")
    

    to mi pise ze posilam value a ne funkci. Nevedel by nekdo prosim?
    JAVAMAN
    JAVAMAN --- ---
    tak ale doufam, ze se s tim nepotkam "in the wild" :D https://youtu.be/buJPwD5nW1g?t=112
    RAGNAROK
    RAGNAROK --- ---
    JAVAMAN:
    to vypada nadejne.
    JAVAMAN
    JAVAMAN --- ---
    https://play.golang.org/p/TvkaGy3l1za nejsem moc mimo s pochopenim otazky?
    RAGNAROK
    RAGNAROK --- ---
    CUCHULAIN:
    Problem je ze kdyz pouziju F(i interface{}) tak tam nemuzu naprasit funkci a kdyz pouziju F(g func() []byte) tak tam zas nemuzu naprasit []byte.
    RAGNAROK
    RAGNAROK --- ---
    CUCHULAIN:
    uplne neobejdu jen chci aby funkce F brala jako vstupni parameter bud funkci konkretniho typu napr. func() []byte, nebo [] byte, nebo nic. To jsou 3 konkretni typy. :-)
    Samozrejme ze to muzu napsat jinak akorat by mo to usetrilo hafo kodu.
    CUCHULAIN
    CUCHULAIN --- ---
    RAGNAROK: jinak testovat typ parametru můžeš - https://golang.org/ref/spec#Type_assertions
    CUCHULAIN
    CUCHULAIN --- ---
    RAGNAROK: a určitě to potřebuješ zrovna takhle?
    bylo by potřeba trochu experimentovat, ale určitě to není ideální řešení. např. tím úplně obejdeš typovou kontrolu, která se při vývoji dost hodí :-)
    RAGNAROK
    RAGNAROK --- ---
    CUCHULAIN:
    No ja bych pro priklad chtel aby kdyz zadam:
    a) F(g()) - aby to vracelo furt stejnej cas tj. vyhodnoti se funckce g jednou a pak F pouziva dokoloa tu hodnotu
    b) F(g) - aby funkce vzdycky vyhodnotila funkci g. Tj. melo by to vracet aktualni cas.
    c) F() - aby to nevracelo nic. resp. nejakou default hodnotu.
    CUCHULAIN
    CUCHULAIN --- ---
    CUCHULAIN: teď teda nevím, jestli je to odpověď na otázku, ale alespoň to vrací čas :-)
    RAGNAROK
    RAGNAROK --- ---
    Potreboval bych definovat funkci F ktera jako vstupni parameter bere funkci "g() interface{}", interface{} nebo nic. Jde to nejak?
    Zkousim:
    a) https://play.golang.org/p/cISsisyUORU
    F(g()) - tohle pise porad stejny cas, nebere nic

    b) https://play.golang.org/p/V3k-z4WNax1
    F(g) - tohle vraci adresu pameti, nebere nic

    c) https://play.golang.org/p/4JXlRY47_6k
    tohle bere nic nebo interface
    CUCHULAIN
    CUCHULAIN --- ---
    RAGNAROK: tak dobrý :-)
    pokud to nepotřebuješ zaokrouhlit na nějaký extrémně vysoký počet des. míst, mělo by to stačit.
    RAGNAROK
    RAGNAROK --- ---
    CUCHULAIN:
    To je divne, dekuji za vyzkouseni. Me to meri tak ze ta tvoje funkce trva ~80 ns a ta moje ~1000 ns.
    CUCHULAIN
    CUCHULAIN --- ---
    RAGNAROK: mě to teda nic moc neměří :-)

    go run RoundBenchmark.go
    2.828356449679806e+19 6 2.828356449679806e+19
    2.828356449679806e+19 6 2.828356449679806e+19
    
    Rounder times: [0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0]
    Rounder mean time: 0
    
    Rounderp times: [0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0]
    Rounderp mean time: 0
    
    RAGNAROK
    RAGNAROK --- ---
    RAGNAROK:
    Zajimalo by me jestli funkce Measurer pujde prepsat tak ze by brala obecnou funkci.
    RAGNAROK
    RAGNAROK --- ---
    CUCHULAIN:
    
    package main
    
    import (
    	"fmt"
    	"math"
    	"math/rand"
    	"strconv"
    	"time"
    
    	"gonum.org/v1/gonum/stat"
    )
    
    func main() {
    	rand.Seed(time.Now().Unix())
    	flt := rand.Float64() * 1e20
    	rand.Seed(time.Now().Unix())
    	flt = flt + rand.Float64()*1e10
    	rand.Seed(time.Now().Unix())
    	flt = flt + rand.Float64()
    
    	plc := rand.Intn(9)
    	num := 100
    
    	fmt.Println(flt, plc, Rounder(flt, plc))
    	fmt.Println(flt, plc, Rounderp(flt, plc))
    	fmt.Println()
    
    	fn1 := Measurer(num, Rounder, flt, plc)
    	fmt.Println("Rounder times:", fn1)
    	fmt.Println("Rounder mean time:", stat.Mean(fn1, nil))
    
    	fmt.Println()
    	fn2 := Measurer(num, Rounderp, flt, plc)
    	fmt.Println("Rounderp times:", fn2)
    	fmt.Println("Rounderp mean time:", stat.Mean(fn2, nil))
    
    }
    
    func Measurer(num int, fn func(par float64, places int) float64, p1 float64, plc int) []float64 {
    	var ott []float64
    	for i := 0; i < num; i++ {
    		t0 := time.Now()
    		fn(p1, plc)
    		t1 := float64(time.Since(t0))
    		ott = append(ott, t1)
    	}
    	return ott
    }
    
    func Rounder(i float64, places int) float64 {
    	frmt := "%." + fmt.Sprint(places) + "f"
    	a, _ := strconv.ParseFloat(fmt.Sprintf(frmt, i), 64)
    	return a
    }
    
    func Rounderp(i float64, places int) float64 {
    	pow := math.Pow10(places)
    	num := math.Round(i*pow) / pow
    	return num
    }
    


    Ten tvuj zpusob je 20x rychlejsi dle horejsiho testu. :)
    CUCHULAIN
    CUCHULAIN --- ---
    RAGNAROK: ok. je možný, že fmt zaokrouhluje. to jsem nezkoušel.
    RAGNAROK
    RAGNAROK --- ---
    CUCHULAIN:
    Jsem tu funkci testoval a zaokrouhluje podle pravidel.
    Stim pow muze byt pro velke cisla problem preteceni.
    Kliknutím sem můžete změnit nastavení reklam