1 package cz.cuni.amis.utils.concurrency;
2
3 import java.util.ArrayList;
4 import java.util.List;
5 import java.util.concurrent.atomic.AtomicLongArray;
6
7 public class AtomicLongList {
8
9 private List<AtomicLongArray> arrays = new ArrayList<AtomicLongArray>();
10
11 private int capacityStep;
12
13 private int size = 0;
14
15 public AtomicLongList(int initialCapacity, int capacityStep) {
16 this.capacityStep = capacityStep;
17 if (initialCapacity > 0) {
18 getArray(initialCapacity-1);
19 }
20 }
21
22 private int arrayIndex(int index) {
23 return index / capacityStep;
24 }
25
26 private int trueIndex(int index) {
27 return index - capacityStep * (index / capacityStep);
28 }
29
30 private AtomicLongArray getArray(int index) {
31 int arrayIndex = arrayIndex(index);
32 if (size <= index) {
33 synchronized(arrays) {
34 if (size <= index) {
35 size = index + 1;
36 }
37 }
38 }
39 if (arrayIndex < arrays.size()) return arrays.get(arrayIndex);
40 synchronized(arrays) {
41 while (arrays.size() <= arrayIndex) arrays.add(new AtomicLongArray(capacityStep));
42 }
43 return arrays.get(arrayIndex);
44 }
45
46
47
48
49
50
51
52
53 public long addAndGet(int i, long delta) {
54 return getArray(i).addAndGet(trueIndex(i), delta);
55 }
56
57
58
59
60
61
62
63
64
65
66 public boolean compareAndSet(int i, long expect, long update) {
67 return getArray(i).compareAndSet(trueIndex(i), expect, update);
68 }
69
70
71
72
73
74
75
76 public long decrementAndGet(int i) {
77 return getArray(i).decrementAndGet(trueIndex(i));
78 }
79
80
81
82
83
84
85
86 public long get(int i) {
87 return getArray(i).get(trueIndex(i));
88 }
89
90
91
92
93
94
95
96
97 public long getAndAdd(int i, long delta) {
98 return getArray(i).getAndAdd(trueIndex(i), delta);
99 }
100
101
102
103
104
105
106
107 public long getAndDecrement(int i) {
108 return getArray(i).getAndDecrement(trueIndex(i));
109 }
110
111
112
113
114
115
116
117 public long getAndIncrement(int i) {
118 return getArray(i).getAndIncrement(trueIndex(i));
119 }
120
121
122
123
124
125
126
127
128
129 public long getAndSet(int i, long newValue) {
130 return getArray(i).getAndSet(trueIndex(i), newValue);
131 }
132
133
134
135
136
137
138
139 public long incrementAndGet(int i) {
140 return getArray(i).incrementAndGet(trueIndex(i));
141 }
142
143
144
145
146
147
148 public int size() {
149 return size;
150 }
151
152
153
154
155
156 public int capacity() {
157 return arrays.size() * capacityStep;
158 }
159
160
161
162
163
164
165
166 public void set(int i, long newValue) {
167 getArray(i).set(trueIndex(i), newValue);
168 }
169
170
171
172
173
174
175
176
177
178
179 public boolean weakCompareAndSet(int i, long expect, long update) {
180 return getArray(i).weakCompareAndSet(trueIndex(i), expect, update);
181 }
182 }