File tree Expand file tree Collapse file tree 3 files changed +67
-0
lines changed Expand file tree Collapse file tree 3 files changed +67
-0
lines changed Original file line number Diff line number Diff line change @@ -115,6 +115,7 @@ const (
115
115
'vlib/vweb/request_test.v' ,
116
116
'vlib/net/http/request_test.v' ,
117
117
'vlib/vweb/route_test.v' ,
118
+ 'vlib/sync/once_test.v' ,
118
119
]
119
120
skip_on_non_windows = [
120
121
'do_not_remove' ,
Original file line number Diff line number Diff line change
1
+ module sync
2
+
3
+ import sync.atomic2
4
+
5
+ pub struct Once {
6
+ mut :
7
+ m RwMutex
8
+ pub :
9
+ count u64
10
+ }
11
+
12
+ // new_once return a new Once struct.
13
+ pub fn new_once () & Once {
14
+ mut once := & Once{}
15
+ once.m.init ()
16
+ return once
17
+ }
18
+
19
+ // do execute the function only once.
20
+ pub fn (mut o Once) do (f fn ()) {
21
+ if atomic2 .load_u64 (& o.count) < 1 {
22
+ o.do_slow (f)
23
+ }
24
+ }
25
+
26
+ fn (mut o Once) do_slow (f fn ()) {
27
+ o.m.@lock ()
28
+ if o.count < 1 {
29
+ atomic2 .store_u64 (& o.count, 1 )
30
+ f ()
31
+ }
32
+ o.m.unlock ()
33
+ }
Original file line number Diff line number Diff line change
1
+ import sync
2
+
3
+ struct One {
4
+ pub mut :
5
+ i int
6
+ }
7
+
8
+ fn (mut o One) add (i int ) {
9
+ o.i = o.i + i
10
+ }
11
+
12
+ fn run (mut once sync.Once, mut o One, c chan bool ) {
13
+ once.do (fn [mut o] () {
14
+ o.add (5 )
15
+ })
16
+ c < - true
17
+ }
18
+
19
+ fn test_once () {
20
+ mut o := & One{}
21
+ mut once := sync.new_once ()
22
+ c := chan bool {}
23
+ n := 10
24
+
25
+ // It is executed 10 times, but only once actually.
26
+ for i := 0 ; i < n; i++ {
27
+ go run (mut once, mut o, c)
28
+ }
29
+ for i := 0 ; i < n; i++ {
30
+ < - c
31
+ }
32
+ assert o.i == 5
33
+ }
You can’t perform that action at this time.
0 commit comments