Skip to content

Commit 73b8d15

Browse files
committed
feat: add solutions to lc problem: No.0552
No.0552.Student Attendance Record II
1 parent c701e89 commit 73b8d15

File tree

2 files changed

+261
-0
lines changed

2 files changed

+261
-0
lines changed

solution/0500-0599/0552.Student Attendance Record II/README.md

Lines changed: 140 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,25 @@
6262

6363
<!-- 这里可写通用的实现逻辑 -->
6464

65+
**方法一:记忆化搜索**
66+
67+
我们设计一个函数 $dfs(i, j, k)$,表示从第 $i$ 个出勤记录开始,当前缺勤次数为 $j$,目前最后连续迟到次数为 $k$ 时,可获得出勤奖励的情况数量。那么答案就是 $dfs(0, 0, 0)$。
68+
69+
函数 $dfs(i, j, k)$ 的执行过程如下:
70+
71+
- 如果 $i \ge n$,说明已经遍历完所有出勤记录,返回 $1$;
72+
- 如果 $j = 0$,说明当前缺勤次数为 $0$,那么可以选择缺勤,即 $dfs(i + 1, j + 1, 0)$;
73+
- 如果 $k \lt 2$,说明当前连续迟到次数小于 $2$,那么可以选择迟到,即 $dfs(i + 1, j, k + 1)$;
74+
- 无论如何,都可以选择到场,即 $dfs(i + 1, j, 0)$。
75+
76+
我们将上述三种情况的结果相加,即为 $dfs(i, j, k)$ 的结果。
77+
78+
为了避免重复计算,我们可以使用记忆化搜索。
79+
80+
时间复杂度 $O(n)$,空间复杂度 $O(n)$。其中 $n$ 为出勤记录的长度。
81+
82+
**方法二:动态规划**
83+
6584
动态规划,定义 `dp[i][j][k]` 表示前 `i` 天,缺勤 `j` 次,连续迟到 `k` 次时,可获得出勤奖励的情况数量
6685

6786
状态转移需要对第 `i` 天的出勤情况分别讨论:
@@ -76,6 +95,27 @@
7695

7796
<!-- 这里可写当前语言的特殊实现逻辑 -->
7897

98+
```python
99+
class Solution:
100+
def checkRecord(self, n: int) -> int:
101+
@cache
102+
def dfs(i, j, k):
103+
if i >= n:
104+
return 1
105+
ans = 0
106+
if j == 0:
107+
ans += dfs(i + 1, j + 1, 0)
108+
if k < 2:
109+
ans += dfs(i + 1, j, k + 1)
110+
ans += dfs(i + 1, j, 0)
111+
return ans % mod
112+
113+
mod = 10**9 + 7
114+
ans = dfs(0, 0, 0)
115+
dfs.cache_clear()
116+
return ans
117+
```
118+
79119
```python
80120
class Solution:
81121
def checkRecord(self, n: int) -> int:
@@ -110,6 +150,37 @@ class Solution:
110150

111151
<!-- 这里可写当前语言的特殊实现逻辑 -->
112152

153+
```java
154+
class Solution {
155+
private final int mod = (int) 1e9 + 7;
156+
private int n;
157+
private Integer[][][] f;
158+
159+
public int checkRecord(int n) {
160+
this.n = n;
161+
f = new Integer[n][2][3];
162+
return dfs(0, 0, 0);
163+
}
164+
165+
private int dfs(int i, int j, int k) {
166+
if (i >= n) {
167+
return 1;
168+
}
169+
if (f[i][j][k] != null) {
170+
return f[i][j][k];
171+
}
172+
int ans = dfs(i + 1, j, 0);
173+
if (j == 0) {
174+
ans = (ans + dfs(i + 1, j + 1, 0)) % mod;
175+
}
176+
if (k < 2) {
177+
ans = (ans + dfs(i + 1, j, k + 1)) % mod;
178+
}
179+
return f[i][j][k] = ans;
180+
}
181+
}
182+
```
183+
113184
```java
114185
class Solution {
115186
private static final int MOD = 1000000007;
@@ -148,6 +219,41 @@ class Solution {
148219

149220
### **Go**
150221

222+
```go
223+
func checkRecord(n int) int {
224+
f := make([][][]int, n)
225+
for i := range f {
226+
f[i] = make([][]int, 2)
227+
for j := range f[i] {
228+
f[i][j] = make([]int, 3)
229+
for k := range f[i][j] {
230+
f[i][j][k] = -1
231+
}
232+
}
233+
}
234+
const mod = 1e9 + 7
235+
var dfs func(i, j, k int) int
236+
dfs = func(i, j, k int) int {
237+
if i >= n {
238+
return 1
239+
}
240+
if f[i][j][k] != -1 {
241+
return f[i][j][k]
242+
}
243+
ans := dfs(i+1, j, 0)
244+
if j == 0 {
245+
ans = (ans + dfs(i+1, j+1, 0)) % mod
246+
}
247+
if k < 2 {
248+
ans = (ans + dfs(i+1, j, k+1)) % mod
249+
}
250+
f[i][j][k] = ans
251+
return ans
252+
}
253+
return dfs(0, 0, 0)
254+
}
255+
```
256+
151257
```go
152258
const _mod int = 1e9 + 7
153259

@@ -190,6 +296,40 @@ func checkRecord(n int) int {
190296

191297
### **C++**
192298

299+
```cpp
300+
int f[100010][2][3];
301+
const int mod = 1e9 + 7;
302+
303+
class Solution {
304+
public:
305+
int checkRecord(int n) {
306+
this->n = n;
307+
memset(f, -1, sizeof(f));
308+
return dfs(0, 0, 0);
309+
}
310+
311+
int dfs(int i, int j, int k) {
312+
if (i >= n) {
313+
return 1;
314+
}
315+
if (f[i][j][k] != -1) {
316+
return f[i][j][k];
317+
}
318+
int ans = dfs(i + 1, j, 0);
319+
if (j == 0) {
320+
ans = (ans + dfs(i + 1, j + 1, 0)) % mod;
321+
}
322+
if (k < 2) {
323+
ans = (ans + dfs(i + 1, j, k + 1)) % mod;
324+
}
325+
return f[i][j][k] = ans;
326+
}
327+
328+
private:
329+
int n;
330+
};
331+
```
332+
193333
```cpp
194334
constexpr int MOD = 1e9 + 7;
195335

solution/0500-0599/0552.Student Attendance Record II/README_EN.md

Lines changed: 121 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,27 @@ Only &quot;AA&quot; is not eligible because there are 2 absences (there need to
5959

6060
### **Python3**
6161

62+
```python
63+
class Solution:
64+
def checkRecord(self, n: int) -> int:
65+
@cache
66+
def dfs(i, j, k):
67+
if i >= n:
68+
return 1
69+
ans = 0
70+
if j == 0:
71+
ans += dfs(i + 1, j + 1, 0)
72+
if k < 2:
73+
ans += dfs(i + 1, j, k + 1)
74+
ans += dfs(i + 1, j, 0)
75+
return ans % mod
76+
77+
mod = 10**9 + 7
78+
ans = dfs(0, 0, 0)
79+
dfs.cache_clear()
80+
return ans
81+
```
82+
6283
```python
6384
class Solution:
6485
def checkRecord(self, n: int) -> int:
@@ -91,6 +112,37 @@ class Solution:
91112

92113
### **Java**
93114

115+
```java
116+
class Solution {
117+
private final int mod = (int) 1e9 + 7;
118+
private int n;
119+
private Integer[][][] f;
120+
121+
public int checkRecord(int n) {
122+
this.n = n;
123+
f = new Integer[n][2][3];
124+
return dfs(0, 0, 0);
125+
}
126+
127+
private int dfs(int i, int j, int k) {
128+
if (i >= n) {
129+
return 1;
130+
}
131+
if (f[i][j][k] != null) {
132+
return f[i][j][k];
133+
}
134+
int ans = dfs(i + 1, j, 0);
135+
if (j == 0) {
136+
ans = (ans + dfs(i + 1, j + 1, 0)) % mod;
137+
}
138+
if (k < 2) {
139+
ans = (ans + dfs(i + 1, j, k + 1)) % mod;
140+
}
141+
return f[i][j][k] = ans;
142+
}
143+
}
144+
```
145+
94146
```java
95147
class Solution {
96148
private static final int MOD = 1000000007;
@@ -129,6 +181,41 @@ class Solution {
129181

130182
### **Go**
131183

184+
```go
185+
func checkRecord(n int) int {
186+
f := make([][][]int, n)
187+
for i := range f {
188+
f[i] = make([][]int, 2)
189+
for j := range f[i] {
190+
f[i][j] = make([]int, 3)
191+
for k := range f[i][j] {
192+
f[i][j][k] = -1
193+
}
194+
}
195+
}
196+
const mod = 1e9 + 7
197+
var dfs func(i, j, k int) int
198+
dfs = func(i, j, k int) int {
199+
if i >= n {
200+
return 1
201+
}
202+
if f[i][j][k] != -1 {
203+
return f[i][j][k]
204+
}
205+
ans := dfs(i+1, j, 0)
206+
if j == 0 {
207+
ans = (ans + dfs(i+1, j+1, 0)) % mod
208+
}
209+
if k < 2 {
210+
ans = (ans + dfs(i+1, j, k+1)) % mod
211+
}
212+
f[i][j][k] = ans
213+
return ans
214+
}
215+
return dfs(0, 0, 0)
216+
}
217+
```
218+
132219
```go
133220
const _mod int = 1e9 + 7
134221

@@ -171,6 +258,40 @@ func checkRecord(n int) int {
171258

172259
### **C++**
173260

261+
```cpp
262+
int f[100010][2][3];
263+
const int mod = 1e9 + 7;
264+
265+
class Solution {
266+
public:
267+
int checkRecord(int n) {
268+
this->n = n;
269+
memset(f, -1, sizeof(f));
270+
return dfs(0, 0, 0);
271+
}
272+
273+
int dfs(int i, int j, int k) {
274+
if (i >= n) {
275+
return 1;
276+
}
277+
if (f[i][j][k] != -1) {
278+
return f[i][j][k];
279+
}
280+
int ans = dfs(i + 1, j, 0);
281+
if (j == 0) {
282+
ans = (ans + dfs(i + 1, j + 1, 0)) % mod;
283+
}
284+
if (k < 2) {
285+
ans = (ans + dfs(i + 1, j, k + 1)) % mod;
286+
}
287+
return f[i][j][k] = ans;
288+
}
289+
290+
private:
291+
int n;
292+
};
293+
```
294+
174295
```cpp
175296
constexpr int MOD = 1e9 + 7;
176297

0 commit comments

Comments
 (0)