-
Notifications
You must be signed in to change notification settings - Fork 5
/
Copy pathCinemaSeatAllocation.java
154 lines (138 loc) · 5.64 KB
/
CinemaSeatAllocation.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
/*https://leetcode.com/problems/cinema-seat-allocation/*/
// class Solution {
// public int maxNumberOfFamilies(int n, int[][] reservedSeats) {
// int groups = 0;
// Map<Integer,Set<Integer>> reservation = new HashMap<Integer,Set<Integer>>();
// for (int i = 1; i <= 8; ++i)
// reservation.put(i, new HashSet<Integer>());
// for (int[] res : reservedSeats)
// if (res[1] != 1 && res[1] != 10)
// reservation.get(res[1]-1).add(res[0]-1);
// for (int i = 0; i < n; ++i)
// {
// if ((!reservation.get(1).contains(i) && !reservation.get(2).contains(i)) || (!reservation.get(7).contains(i) && !reservation.get(8).contains(i)))
// {
// if (!reservation.get(1).contains(i) && !reservation.get(2).contains(i) && !reservation.get(3).contains(i) && !reservation.get(4).contains(i))
// ++groups;
// if (!reservation.get(5).contains(i) && !reservation.get(6).contains(i) && !reservation.get(7).contains(i) && !reservation.get(8).contains(i))
// ++groups;
// }
// else if (!reservation.get(3).contains(i) && !reservation.get(4).contains(i) && !reservation.get(5).contains(i) && !reservation.get(6).contains(i))
// ++groups;
// }
// return groups;
// }
// }
class Solution {
public int maxNumberOfFamilies(int n, int[][] reservedSeats) {
int groups = 0;
Arrays.sort(reservedSeats,(a,b)->(a[0]==b[0] ? a[1]-b[1] : a[0]-b[0]));
boolean isType1 = true, isType2 = true, isType3Left = true, isType3Right = true;
int currRow = reservedSeats[0][0];
int blankRowCount = reservedSeats[0][0]-1;
groups += (2*blankRowCount);
for (int[] r : reservedSeats)
{
if (r[0] != currRow)
{
blankRowCount = r[0]-currRow-1;
groups += (2*blankRowCount);
if (!isType1 && !isType2)
{
if (isType3Left && isType3Right)
++groups;
}
else
{
if (isType1 && isType3Left) ++groups;
if (isType2 && isType3Right) ++groups;
}
currRow = r[0];
isType1 = isType2 = isType3Left = isType3Right = true;
}
if (r[1] == 2 || r[1] == 3)
isType1 = false;
if (r[1] == 8 || r[1] == 9)
isType2 = false;
if (r[1] == 4 || r[1] == 5)
isType3Left = false;
if (r[1] == 6 || r[1] == 7)
isType3Right = false;
}
blankRowCount = n-currRow;
groups += (2*blankRowCount);
if (!isType1 && !isType2)
{
if (isType3Left && isType3Right)
++groups;
}
else
{
if (isType1 && isType3Left) ++groups;
if (isType2 && isType3Right) ++groups;
}
return groups;
}
}
//cleaner version of the above solution
class Solution {
public int maxNumberOfFamilies(int n, int[][] reservedSeats) {
//Sort revervations by row.
Arrays.sort(reservedSeats, (a, b) -> a[0] - b[0]);
//Assume all rows can hold 2 groups.
int count = 2 * n;
int ptr = 0;
while (ptr < reservedSeats.length) {
//Assume that all 3 groups in the row are possible.
boolean[] blocks = new boolean[] {true, true, true};
int row = reservedSeats[ptr][0];
//Process all reservations in the current row.
while (ptr < reservedSeats.length && row == reservedSeats[ptr][0]) {
int col = reservedSeats[ptr][1];
if (col > 1 && col < 6)
blocks[0] = false;
if (col > 3 && col < 8)
blocks[1] = false;
if (col > 5 && col < 10)
blocks[2] = false;
++ptr;
}
//If 2 groups are possible, then do nothing.
if (blocks[0] && blocks[2])
continue;
//If only 1 group is possible, then subtract one from total.
else if (blocks[0] || blocks[1] || blocks[2])
count--;
//No groups possible, subtract 2.
else
count -= 2;
}
return count;
}
}
//efficient solution
class Solution {
public int maxNumberOfFamilies(int n, int[][] reservedSeats) {
Map<Integer, Integer> map = new HashMap<>();
//For each reserved ticket, updated the bitmap for that row.
for (int[] seat: reservedSeats) {
int row = seat[0], col = seat[1];
map.put(row, map.getOrDefault(row, 0) | (1 << (col - 1)));
}
//Assume all rows can hold 2 groups.
int count = 2 * n;
for (int bitmap: map.values()) {
boolean isBlock0Available = (bitmap & 30) == 0, isBlock1Available = (bitmap & 120) == 0, isBlock2Available = (bitmap & 480) == 0;
//If 2 groups are possible, then they are already included in total count.
if (isBlock0Available && isBlock2Available)
continue;
//If only 1 group is possible, then we need to subtract one.
else if (isBlock0Available || isBlock1Available || isBlock2Available)
count--;
//No groups possible -- need to subtract 2.
else
count -= 2;
}
return count;
}
}