E. 2 канала

Верно решивших: 62
Рейтинг быстрых решений
Очень похожие решения учитываются в рейтинге один раз.
1 2 3 4 5
Время отправки: 2020-06-03 13:14:32 ID: 392 Время: 0.154s
package main import ( "sync" ) type res struct { value int } type calcResults struct { mx sync.RWMutex m map[int]int } func newCalcResults() *calcResults { return &calcResults{m: make(map[int]int, 0)} } func (c *calcResults) Load(key int) (int, bool) { c.mx.RLock() defer c.mx.RUnlock() val, ok := c.m[key] return val, ok } func (c *calcResults) Store(key int, value int) { c.mx.Lock() defer c.mx.Unlock() c.m[key] = value } func Merge2Channels(f func(int) int, in1 <-chan int, in2 <-chan int, out chan<- int, n int) { go func() { var calcResults = newCalcResults() var results = make([]*res, n) for i := 0; i < n; i++ { x1 := <-in1 x2 := <-in2 go func(x1 int, x2 int, idx int) { var calcWg sync.WaitGroup if x1 == x2{ resX1, ok := calcResults.Load(x1) if !ok { calcWg.Add(1) go func() { resX1 = f(x1) calcResults.Store(x1, resX1) calcWg.Done() }() } calcWg.Wait() results[idx] = &res{value: resX1 *2} } else { resX1, ok := calcResults.Load(x1) if !ok { calcWg.Add(1) go func() { resX1 = f(x1) calcResults.Store(x1, resX1) calcWg.Done() }() } resX2, ok := calcResults.Load(x2) if !ok { calcWg.Add(1) go func() { resX2 = f(x2) calcResults.Store(x2, resX2) calcWg.Done() }() } calcWg.Wait() results[idx] = &res{value: resX1 + resX2} } }(x1, x2, i) } index := 0 for { if results[index] != nil { out <- results[index].value index++ } if index >= n { break } } close(out) }() }
Время отправки: 2020-06-02 08:26:24 ID: 361 Время: 0.161s
package main func Merge2Channels(f func(int) int, in1 <-chan int, in2 <-chan int, out chan<- int, n int) { // type to store f result type Tres struct { Index int Value int Count int8 } // func to evaluate f in goroutine evalF := func(index int, val int, output chan<- Tres) { output <- Tres{index, f(val), 0} } evalFNTimes := func(in <-chan int, output chan<- Tres) { for i := 0; i < n; i++ { go evalF(i, <-in, output) } } go func() { // chan for f results fChan := make(chan Tres) // map to store result for out resMap := make(map[int]Tres) go evalFNTimes(in1, fChan) go evalFNTimes(in2, fChan) for i := 0; i < n; { if r := resMap[i]; r.Count == 2 { out <- r.Value delete(resMap, i) i++ continue } select { case res := <-fChan: // save to map, sum result and increase counter r := resMap[res.Index] r.Value += res.Value r.Count++ resMap[res.Index] = r default: } } }() }
Время отправки: 2020-05-31 12:33:21 ID: 192 Время: 0.161s
package main func Merge2Channels(f func(int) int, in1 <-chan int, in2 <-chan int, out chan<- int, n int) { go func(f func(int) int, in1 <-chan int, in2 <-chan int, out chan<- int, n int) { f1res := make([]*int, n) f2res := make([]*int, n) go func() { i := 0 for true { if f1res[i] != nil && f2res[i] != nil { res := *f1res[i] + *f2res[i] out <- res if i++; i == n { break } } } }() input := func(input <-chan int, results []*int) { for i := 0; i < n; i++ { x := <-input go func(i int, x int) { res := f(x) results[i] = &res }(i, x) } } go input(in1, f1res) go input(in2, f2res) }(f, in1, in2, out, n) }
Время отправки: 2020-06-02 11:28:24 ID: 371 Время: 0.162s
package main import ( "sync" ) func ExecuteFunc(index int, f func(int) int, x int, mut *sync.Mutex, resultArray []int, finish chan<- int) { result := f(x) mut.Lock() resultArray[index] = result mut.Unlock() finish <- index } func readChannel(chanNum int, f func(int) int, in1 <-chan int, muResult *sync.Mutex, resultArray []int, n int, finish chan<- int) { for i := 0; i < n; i++ { value := <-in1 go ExecuteFunc(i, f, value, muResult, resultArray, finish) } } func Iterate(f func(int) int, in1 <-chan int, in2 <-chan int, out chan<- int, n int) { result1Array := make([]int, n, n) result2Array := make([]int, n, n) done := make(chan int, 2*n) muResult1 := &sync.Mutex{} muResult2 := &sync.Mutex{} go readChannel(1, f, in1, muResult1, result1Array, n, done) go readChannel(2, f, in2, muResult2, result2Array, n, done) i := 0 doneArray := make([]int, n, n) for i < n { select { case val := <-done: doneArray[val]++ default: break } if doneArray[i] == 2 { muResult1.Lock() muResult2.Lock() out <- result1Array[i] + result2Array[i] muResult1.Unlock() muResult2.Unlock() i++ } } } func Merge2Channels(f func(int) int, in1 <-chan int, in2 <-chan int, out chan<- int, n int) { go Iterate(f, in1, in2, out, n) }
Время отправки: 2020-06-02 09:19:51 ID: 366 Время: 0.201s
package main import ( "sync" ) var ( mtx = new(sync.Mutex) tasksQueue = make(chan task, 100000) ) type task struct{ function func(int) int inputChannel1 <-chan int inputChannel2 <-chan int outputChannel chan<- int iterations int } type ConcurrentSlice struct { sync.RWMutex slice []*int } func NewConcurrentSlice (size int) *ConcurrentSlice { return &ConcurrentSlice{ slice: make([]*int, size), } } func (cs *ConcurrentSlice) Get(key int) (*int,) { cs.RLock() value := cs.slice[key] cs.RUnlock() return value } func (cs *ConcurrentSlice) Set(key int, value *int) { cs.Lock() cs.slice[key] = value cs.Unlock() } func calculateFunction(function func(int) int, inputChannel <-chan int, outputSlice *ConcurrentSlice, iterationsCount int) { for i := 0; i < iterationsCount; i ++ { ii := i select { case curNumber := <-inputChannel: go func(ni, value int) { curResult := function(curNumber) outputSlice.Set(ni, &curResult) }(ii, curNumber) } } } func Merge2Channels(f func(int) int, in1 <-chan int, in2 <-chan int, out chan<- int, n int) { tasksQueue <- task{ function: f, inputChannel1: in1, inputChannel2: in2, outputChannel: out, iterations: n, } go func() { var ( passedIterations = 0 functionResults1 = NewConcurrentSlice(n) functionResults2 = NewConcurrentSlice(n) ) mtx.Lock() currentTask := <- tasksQueue go calculateFunction(currentTask.function, currentTask.inputChannel1, functionResults1, currentTask.iterations) //, wg) go calculateFunction(currentTask.function, currentTask.inputChannel2, functionResults2, currentTask.iterations) //, wg) for { firstResult := functionResults1.Get(passedIterations) secondResult := functionResults2.Get(passedIterations) if firstResult != nil && secondResult != nil { currentTask.outputChannel <- *firstResult + *secondResult passedIterations += 1 if passedIterations >= n { mtx.Unlock() return } } } }() }
Время отправки: 2020-05-31 12:12:47 ID: 168 Время: 0.202s
package main import ( "sync" ) var nMutex sync.Mutex type Result struct { out chan<- int value int } func Merge2Channels(f func(int) int, in1 <-chan int, in2 <-chan int, out chan<- int, n int) { go func() { nMutex.Lock() var waitingChans []chan Result for i := 0; i < n; i++ { x1, x2 := <-in1, <-in2 waitingChan := make(chan Result, 1) waitingChans = append(waitingChans, waitingChan) go func(x1, x2 int, waitingChan chan Result) { waitingChan <- Result{out, f(x1) + f(x2)} }(x1, x2, waitingChan) } for _, waitingChan := range waitingChans { result := <-waitingChan result.out <- result.value } nMutex.Unlock() }() }
Время отправки: 2020-05-31 12:14:44 ID: 173 Время: 0.203s
package main import ( "sync" ) var jobsMutex, nMutex sync.Mutex type Pair struct { x1, x2 int out chan<- int f func(int) int } type Result struct { out chan<- int value int x1, x2 int } var jobs = make(chan Pair) func worker(n int, done chan bool) { jobsMutex.Lock() var waitingChans []chan Result for i := 0; i < n; i++ { pair := <-jobs waitingChan := make(chan Result, 1) waitingChans = append(waitingChans, waitingChan) go func(pair Pair, waitingChan chan Result) { waitingChan <- Result{pair.out, pair.f(pair.x1) + pair.f(pair.x2), pair.x1, pair.x2} }(pair, waitingChan) } for _, waitingChan := range waitingChans { result := <-waitingChan result.out <- result.value } jobsMutex.Unlock() done <- true } func Merge2Channels(f func(int) int, in1 <-chan int, in2 <-chan int, out chan<- int, n int) { done := make(chan bool) go worker(n, done) go func() { nMutex.Lock() for i := 0; i < n; i++ { x1, x2 := <-in1, <-in2 pair := Pair{x1, x2, out, f} jobs <- pair } nMutex.Unlock() <-done }() }
Время отправки: 2020-06-02 09:14:18 ID: 365 Время: 0.203s
package main type Terms struct { x int y int } func MergeChannels(in1 <-chan int, in2 <-chan int, repeat int) chan Terms { var out = make(chan Terms, repeat) go func() { for i := 0; i < repeat; i++ { out <- Terms{x: <-in1, y: <-in2} } }() return out } func CalcFunction(merged chan Terms, f func(int) int, repeat int) []chan int { var outChans = make([]chan int, repeat) for i := 0; i < repeat; i++ { out := make(chan int) outChans[i] = out terms := <- merged go func() { out <- f(terms.x) + f(terms.y) }() } return outChans } var syncChan = make(chan int, 1) func Merge2Channels(f func(int) int, in1 <-chan int, in2 <-chan int, out chan<- int, n int) { go func() { syncChan <- 1 merge := MergeChannels(in1, in2, n) calc := CalcFunction(merge, f, n) for i := 0; i < n; i++ { out<- <-calc[i] } <- syncChan }() }
Время отправки: 2020-05-31 13:47:07 ID: 239 Время: 0.203s
package main import ( "sync" ) var gmtx sync.Mutex func Merge2Channels(f func(int) int, in1 <-chan int, in2 <-chan int, out chan<- int, n int) { go func(mf func(int) int, min1 <-chan int, min2 <-chan int, mout chan<- int, mn int) { gmtx.Lock() c := make(chan struct{}) res := make(chan chan int, 50000) go func(am int) { for i := 0; i < am; i++ { mout <- <-<-res } c <- struct{}{} close(res) }(mn) calc := func( iMf func(int) int, val1 int, val2 int, ) chan int { r := make(chan int, 1) inCalc := func( iMf func(int) int, val1 int, val2 int, r chan int, ) { r <- iMf(val1) + iMf(val2) close(r) } go inCalc(iMf, val1, val2, r) return r } for i := 0; i < mn; i++ { res <- calc(mf, <-min1, <-min2) } <-c close(c) gmtx.Unlock() }(f, in1, in2, out, n) }
Время отправки: 2020-05-31 12:12:10 ID: 165 Время: 1.329s
package main import ( "container/list" "sync" "sync/atomic" ) var jobsMutex, nMutex sync.Mutex type Pair struct { x1, x2 int out chan<- int } type Result struct { out chan<- int value int } var jobs = make(chan Pair) var count int64 func master(f func(int) int) { jobsMutex.Lock() var q = list.New() var w sync.WaitGroup var wcc []chan Result loop: for { select { case pair := <-jobs: q.PushBack(pair) atomic.AddInt64(&count, -1) default: if atomic.LoadInt64(&count) <= 0 { break loop } } } for q.Len() > 0 { e := q.Front() pair := e.Value.(Pair) wc := make(chan Result, 1) wcc = append(wcc, wc) w.Add(1) go func(pair Pair, wc chan Result) { wc <- Result{pair.out, f(pair.x1) + f(pair.x2)} }(pair, wc) q.Remove(e) } for _, wc := range wcc { r := <-wc r.out <- r.value w.Done() } w.Wait() jobsMutex.Unlock() } func Merge2Channels(f func(int) int, in1 <-chan int, in2 <-chan int, out chan<- int, n int) { atomic.AddInt64(&count, int64(n)) go master(f) go func() { nMutex.Lock() for i := 0; i < n; i++ { x1, x2 := <-in1, <-in2 pair := Pair{x1, x2, out} jobs <- pair } nMutex.Unlock() }() }
1 2 3 4 5