1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18 package org.apache.giraph.edge;
19
20 import java.io.DataInput;
21 import java.io.DataOutput;
22 import java.io.IOException;
23 import java.util.Iterator;
24 import java.util.NoSuchElementException;
25
26 import org.apache.giraph.conf.ImmutableClassesGiraphConfigurable;
27 import org.apache.giraph.conf.ImmutableClassesGiraphConfiguration;
28 import org.apache.giraph.types.ops.PrimitiveIdTypeOps;
29 import org.apache.giraph.types.ops.TypeOpsUtils;
30 import org.apache.giraph.types.ops.collections.array.WArrayList;
31 import org.apache.giraph.utils.EdgeIterables;
32 import org.apache.hadoop.io.NullWritable;
33 import org.apache.hadoop.io.Writable;
34 import org.apache.hadoop.io.WritableComparable;
35
36
37
38
39
40
41
42
43
44
45 public class IdAndNullArrayEdges<I extends WritableComparable>
46 implements ReuseObjectsOutEdges<I, NullWritable>,
47 MutableOutEdges<I, NullWritable>,
48 ImmutableClassesGiraphConfigurable<I, Writable, NullWritable> {
49
50
51 private WArrayList<I> neighbors;
52
53 @Override
54 public
55 ImmutableClassesGiraphConfiguration<I, Writable, NullWritable> getConf() {
56 throw new UnsupportedOperationException();
57 }
58
59 @Override
60 public void setConf(
61 ImmutableClassesGiraphConfiguration<I, Writable, NullWritable> conf) {
62 PrimitiveIdTypeOps<I> idTypeOps =
63 TypeOpsUtils.getPrimitiveIdTypeOps(conf.getVertexIdClass());
64 neighbors = idTypeOps.createArrayList(10);
65 if (!conf.getEdgeValueClass().equals(NullWritable.class)) {
66 throw new IllegalArgumentException(
67 "IdAndNullArrayEdges can be used only with NullWritable " +
68 "as edgeValueClass, not with " + conf.getEdgeValueClass());
69 }
70 }
71
72 @Override
73 public void initialize(Iterable<Edge<I, NullWritable>> edges) {
74 EdgeIterables.initialize(this, edges);
75 }
76
77 @Override
78 public void initialize(int capacity) {
79 neighbors.clear();
80 neighbors.setCapacity(capacity);
81 }
82
83 @Override
84 public void initialize() {
85 initialize(10);
86 }
87
88 @Override
89 public void add(Edge<I, NullWritable> edge) {
90 neighbors.addW(edge.getTargetVertexId());
91 }
92
93
94
95
96
97 private void trim() {
98 if (neighbors.capacity() > 4 * neighbors.size()) {
99 neighbors.setCapacity(neighbors.size() * 2);
100 }
101 }
102
103
104
105
106
107
108 private void removeAt(int i) {
109
110
111
112 I tmpValue = neighbors.getElementTypeOps().create();
113 neighbors.popIntoW(tmpValue);
114 if (i != neighbors.size()) {
115 neighbors.setW(i, tmpValue);
116 }
117
118 trim();
119 }
120
121 @Override
122 public void remove(I targetVertexId) {
123
124
125 I tmpValue = neighbors.getElementTypeOps().create();
126 for (int i = neighbors.size() - 1; i >= 0; --i) {
127 neighbors.getIntoW(i, tmpValue);
128 if (tmpValue.equals(targetVertexId)) {
129 removeAt(i);
130 }
131 }
132 }
133
134 @Override
135 public int size() {
136 return neighbors.size();
137 }
138
139 @Override
140 public Iterator<Edge<I, NullWritable>> iterator() {
141
142
143
144 return (Iterator) mutableIterator();
145 }
146
147 @Override
148 public Iterator<MutableEdge<I, NullWritable>> mutableIterator() {
149 return new Iterator<MutableEdge<I, NullWritable>>() {
150
151 private int offset = 0;
152
153 private final MutableEdge<I, NullWritable> representativeEdge =
154 EdgeFactory.createReusable(neighbors.getElementTypeOps().create());
155
156 @Override
157 public boolean hasNext() {
158 return offset < neighbors.size();
159 }
160
161 @Override
162 public MutableEdge<I, NullWritable> next() {
163 if (!hasNext()) {
164 throw new NoSuchElementException();
165 }
166 neighbors.getIntoW(offset++, representativeEdge.getTargetVertexId());
167 return representativeEdge;
168 }
169
170 @Override
171 public void remove() {
172
173
174
175 removeAt(--offset);
176 }
177 };
178 }
179
180 @Override
181 public void write(DataOutput out) throws IOException {
182 neighbors.write(out);
183 }
184
185 @Override
186 public void readFields(DataInput in) throws IOException {
187 neighbors.readFields(in);
188 }
189 }