Skip to content

Commit fc7632b

Browse files
committed
Segment Tree Java code with comments
1 parent be90705 commit fc7632b

File tree

1 file changed

+124
-0
lines changed

1 file changed

+124
-0
lines changed
Lines changed: 124 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,124 @@
1+
package Java;
2+
3+
import java.util.Scanner;
4+
5+
public class SegmentTree {
6+
private final int MAX= 1000*1000;
7+
8+
private final int [] originalValues = new int[MAX];
9+
private final int [] segmentSum = new int[MAX * 4];
10+
11+
//Get sum of range [x,y] over segment [left, right] with segId
12+
int getSum(int segId, int left, int right, int x, int y){
13+
if ((y < left) || (right < x)) {
14+
//no intersection
15+
return 0;
16+
} else {
17+
//Two ranges somehow intersects.
18+
if ((x <= left) && (right <= y)) {
19+
//we need all values of [left, right]
20+
return segmentSum[segId];
21+
} else {
22+
//Partly intersects
23+
final int mid = (left+right)/2;
24+
//Get sum of range [x,y] over first half of segment: [left, mid]
25+
final int sumLeft = getSum(segId*2, left, mid, x, y);
26+
//Get sum of range [x,y] over second half of segment: [mid+1, right]
27+
final int sumRight = getSum(segId*2+1, mid+1, right, x, y);
28+
29+
return sumLeft + sumRight;
30+
}
31+
}
32+
}
33+
34+
//Update the value of p-th element, for range [left,right] with segId
35+
void update(int segId, int left, int right, int p, int value) {
36+
if (left == right) {
37+
//it's a node, so sum is equal to the value
38+
segmentSum[segId] = value;
39+
} else {
40+
final int mid = (left+right)/2;
41+
if(p <= mid) {
42+
//continue updating for only the first half of segment [left, mid]
43+
update(segId*2, left, mid, p, value);
44+
}
45+
else {
46+
//continue updating for only the second half of segment [mid+1, right]
47+
update(segId*2+1, mid+1, right, p, value);
48+
}
49+
//Since either half is updated, we also keep the segment updated
50+
segmentSum[segId] = segmentSum[segId*2] + segmentSum[segId*2+1];
51+
}
52+
}
53+
54+
//Build for range [left,right]
55+
void build(int id, int left, int right){
56+
if(left == right) {
57+
//it's a node, so sum is equal to the element
58+
segmentSum[id] = originalValues[left];
59+
} else {
60+
final int mid = (left+right)/2;
61+
//build for range [left, mid]
62+
build(id*2, left, mid);
63+
//build for range [mid+1, right]
64+
build(id*2+1, mid+1, right);
65+
66+
//total sum of segment id is calculated from it's two children
67+
segmentSum[id] = segmentSum[id*2] + segmentSum[id*2 + 1];
68+
}
69+
}
70+
71+
private void run() {
72+
final Scanner scan = new Scanner(System.in);
73+
System.out.println("Please enter the number of elements and number of queries:");
74+
final int n = scan.nextInt();
75+
final int queryNum = scan.nextInt();
76+
77+
System.out.println(String.format("Please enter the %d elements.",n));
78+
for(int i=1; i<=n; i++) {
79+
originalValues[i] = scan.nextInt();
80+
}
81+
82+
//Build the tree and calculate the sums.
83+
build(1, 1, n);
84+
85+
System.out.println(String.format("Please enter the %d queries. Op x y.",queryNum));
86+
System.out.println("Op=1 to get sum of interval [x,y].");
87+
System.out.println("Op=2 to get update value of x-th element to y.");
88+
for (int query=0; query < queryNum ; query+=1) {
89+
final int operation = scan.nextInt();
90+
final int x = scan.nextInt();
91+
final int y = scan.nextInt();
92+
if (operation == 1) {
93+
//Print the sum of segment [x,y]. We start from segment [1,n] with id=1
94+
System.out.println(getSum(1, 1, n, x, y));
95+
} else {
96+
//Update the value of x-th element to y.
97+
//We recursively update the sum starting from segment [1,n] with id=1
98+
update(1, 1, n, x, y);
99+
}
100+
}
101+
}
102+
/*
103+
Sample input:
104+
6 6
105+
3 4 1 6 3 3
106+
1 1 4
107+
1 2 5
108+
2 4 2
109+
1 4 6
110+
2 1 13
111+
1 1 6
112+
113+
Sample output:
114+
14
115+
14
116+
8
117+
26
118+
*/
119+
120+
public static void main(String[] args) {
121+
new SegmentTree().run();
122+
}
123+
124+
}

0 commit comments

Comments
 (0)